blob: 63b0a6af68fa04a52af906ce74a2a5e68a578ee3 [file] [log] [blame]
Junji Watanabe1f67d552022-11-18 00:53:50 +00001#!/usr/bin/env python3
2# Copyright 2022 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"""This script is a wrapper around the ninja binary that is pulled to
6third_party as part of gclient sync. It will automatically find the ninja
7binary when run inside a gclient source tree, so users can just type
8"ninja" on the command line."""
9
10import os
11import subprocess
12import sys
13
14import gclient_paths
15
Junji Watanabe1f67d552022-11-18 00:53:50 +000016
17def findNinjaInPath():
18 env_path = os.getenv('PATH')
19 if not env_path:
20 return
21 exe = 'ninja'
22 if sys.platform in ['win32', 'cygwin']:
23 exe += '.exe'
24 for bin_dir in env_path.split(os.pathsep):
25 if bin_dir.rstrip(os.sep).endswith('depot_tools'):
26 # skip depot_tools to avoid calling ninja.py infitely.
27 continue
28 ninja_path = os.path.join(bin_dir, exe)
29 if os.path.isfile(ninja_path):
30 return ninja_path
31
32
33def fallback(ninja_args):
34 # Try to find ninja in PATH.
35 ninja_path = findNinjaInPath()
36 if ninja_path:
37 return subprocess.call([ninja_path] + ninja_args)
38
Junji Watanabe8f411772023-01-30 02:37:25 +000039 print(
40 'depot_tools/ninja.py: Could not find Ninja in the third_party of '
41 'the current project, nor in your PATH.\n'
Wan-Teh Changbadcbc52023-04-03 19:23:16 +000042 'Please take one of the following actions to install Ninja:\n'
43 '- If your project has DEPS, add a CIPD Ninja dependency to DEPS.\n'
Edman Anjos543fdf32023-02-27 17:33:20 +000044 '- Otherwise, add Ninja to your PATH *after* depot_tools.',
Junji Watanabe8f411772023-01-30 02:37:25 +000045 file=sys.stderr)
46 return 1
Junji Watanabe1f67d552022-11-18 00:53:50 +000047
48
49def main(args):
Junji Watanabe2b1aa8d2023-01-10 02:20:13 +000050 # On Windows the ninja.bat script passes along the arguments enclosed in
51 # double quotes. This prevents multiple levels of parsing of the special '^'
52 # characters needed when compiling a single file. When this case is detected,
53 # we need to split the argument. This means that arguments containing actual
54 # spaces are not supported by ninja.bat, but that is not a real limitation.
55 if (sys.platform.startswith('win') and len(args) == 2):
Loic Sharmae3fe0272023-02-02 21:55:21 +000056 args = args[:1] + args[1].split()
Junji Watanabe2b1aa8d2023-01-10 02:20:13 +000057
Junji Watanabe3e7206f2023-01-11 02:33:26 +000058 # macOS's python sets CPATH, LIBRARY_PATH, SDKROOT implicitly.
59 # https://openradar.appspot.com/radar?id=5608755232243712
60 #
Wan-Teh Changef6c3062023-04-03 23:03:10 +000061 # Removing those environment variables to avoid affecting clang's behaviors.
Junji Watanabe3e7206f2023-01-11 02:33:26 +000062 if sys.platform == 'darwin':
63 os.environ.pop("CPATH", None)
64 os.environ.pop("LIBRARY_PATH", None)
65 os.environ.pop("SDKROOT", None)
66
Junji Watanabe1f67d552022-11-18 00:53:50 +000067 # Get gclient root + src.
68 primary_solution_path = gclient_paths.GetPrimarySolutionPath()
Junji Watanabe1f67d552022-11-18 00:53:50 +000069 gclient_root_path = gclient_paths.FindGclientRoot(os.getcwd())
Shelley Vohr106754b2023-02-01 11:59:40 +000070 gclient_src_root_path = None
71 if gclient_root_path:
72 gclient_src_root_path = os.path.join(gclient_root_path, 'src')
73
74 for base_path in set(
75 [primary_solution_path, gclient_root_path, gclient_src_root_path]):
Brian Osmana0cf4322022-11-18 17:17:21 +000076 if not base_path:
77 continue
Junji Watanabe1f67d552022-11-18 00:53:50 +000078 ninja_path = os.path.join(base_path, 'third_party', 'ninja',
79 'ninja' + gclient_paths.GetExeSuffix())
80 if os.path.isfile(ninja_path):
81 return subprocess.call([ninja_path] + args[1:])
82
83 return fallback(args[1:])
84
85
86if __name__ == '__main__':
Junji Watanabe22bbba12022-12-09 02:18:05 +000087 try:
88 sys.exit(main(sys.argv))
89 except KeyboardInterrupt:
90 sys.exit(1)