tools_webrtc dir converted to py3 + top level PRESUBMIT script
Bug: webrtc:13607
Change-Id: Ib018e43ea977cc24dd71048e68e3343741f7f31b
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/249083
Reviewed-by: Mirko Bonadei <mbonadei@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Reviewed-by: Jeremy Leconte <jleconte@google.com>
Commit-Queue: Christoffer Jansson <jansson@google.com>
Cr-Commit-Position: refs/heads/main@{#35953}
diff --git a/tools_webrtc/ios/build_ios_libs.py b/tools_webrtc/ios/build_ios_libs.py
index f0b2826..15a912e 100755
--- a/tools_webrtc/ios/build_ios_libs.py
+++ b/tools_webrtc/ios/build_ios_libs.py
@@ -1,4 +1,4 @@
-#!/usr/bin/env python
+#!/usr/bin/env vpython3
# Copyright (c) 2017 The WebRTC project authors. All Rights Reserved.
#
@@ -51,303 +51,296 @@
def _ParseArgs():
- parser = argparse.ArgumentParser(description=__doc__)
- parser.add_argument('--build_config',
- default='release',
- choices=['debug', 'release'],
- help='The build config. Can be "debug" or "release". '
- 'Defaults to "release".')
- parser.add_argument(
- '--arch',
- nargs='+',
- default=DEFAULT_ARCHS,
- choices=ENABLED_ARCHS,
- help='Architectures to build. Defaults to %(default)s.')
- parser.add_argument(
- '-c',
- '--clean',
- action='store_true',
- default=False,
- help='Removes the previously generated build output, if any.')
- parser.add_argument(
- '-p',
- '--purify',
- action='store_true',
- default=False,
- help='Purifies the previously generated build output by '
- 'removing the temporary results used when (re)building.')
- parser.add_argument(
- '-o',
- '--output-dir',
- type=os.path.abspath,
- default=SDK_OUTPUT_DIR,
- help='Specifies a directory to output the build artifacts to. '
- 'If specified together with -c, deletes the dir.')
- parser.add_argument(
- '-r',
- '--revision',
- type=int,
- default=0,
- help='Specifies a revision number to embed if building the framework.')
- parser.add_argument('-e',
- '--bitcode',
- action='store_true',
- default=False,
- help='Compile with bitcode.')
- parser.add_argument('--verbose',
- action='store_true',
- default=False,
- help='Debug logging.')
- parser.add_argument('--use-goma',
- action='store_true',
- default=False,
- help='Use goma to build.')
- parser.add_argument(
- '--extra-gn-args',
- default=[],
- nargs='*',
- help='Additional GN args to be used during Ninja generation.')
+ parser = argparse.ArgumentParser(description=__doc__)
+ parser.add_argument('--build_config',
+ default='release',
+ choices=['debug', 'release'],
+ help='The build config. Can be "debug" or "release". '
+ 'Defaults to "release".')
+ parser.add_argument('--arch',
+ nargs='+',
+ default=DEFAULT_ARCHS,
+ choices=ENABLED_ARCHS,
+ help='Architectures to build. Defaults to %(default)s.')
+ parser.add_argument(
+ '-c',
+ '--clean',
+ action='store_true',
+ default=False,
+ help='Removes the previously generated build output, if any.')
+ parser.add_argument('-p',
+ '--purify',
+ action='store_true',
+ default=False,
+ help='Purifies the previously generated build output by '
+ 'removing the temporary results used when (re)building.')
+ parser.add_argument(
+ '-o',
+ '--output-dir',
+ type=os.path.abspath,
+ default=SDK_OUTPUT_DIR,
+ help='Specifies a directory to output the build artifacts to. '
+ 'If specified together with -c, deletes the dir.')
+ parser.add_argument(
+ '-r',
+ '--revision',
+ type=int,
+ default=0,
+ help='Specifies a revision number to embed if building the framework.')
+ parser.add_argument('-e',
+ '--bitcode',
+ action='store_true',
+ default=False,
+ help='Compile with bitcode.')
+ parser.add_argument('--verbose',
+ action='store_true',
+ default=False,
+ help='Debug logging.')
+ parser.add_argument('--use-goma',
+ action='store_true',
+ default=False,
+ help='Use goma to build.')
+ parser.add_argument(
+ '--extra-gn-args',
+ default=[],
+ nargs='*',
+ help='Additional GN args to be used during Ninja generation.')
- return parser.parse_args()
+ return parser.parse_args()
def _RunCommand(cmd):
- logging.debug('Running: %r', cmd)
- subprocess.check_call(cmd, cwd=SRC_DIR)
+ logging.debug('Running: %r', cmd)
+ subprocess.check_call(cmd, cwd=SRC_DIR)
def _CleanArtifacts(output_dir):
- if os.path.isdir(output_dir):
- logging.info('Deleting %s', output_dir)
- shutil.rmtree(output_dir)
+ if os.path.isdir(output_dir):
+ logging.info('Deleting %s', output_dir)
+ shutil.rmtree(output_dir)
def _CleanTemporary(output_dir, architectures):
- if os.path.isdir(output_dir):
- logging.info('Removing temporary build files.')
- for arch in architectures:
- arch_lib_path = os.path.join(output_dir, arch)
- if os.path.isdir(arch_lib_path):
- shutil.rmtree(arch_lib_path)
+ if os.path.isdir(output_dir):
+ logging.info('Removing temporary build files.')
+ for arch in architectures:
+ arch_lib_path = os.path.join(output_dir, arch)
+ if os.path.isdir(arch_lib_path):
+ shutil.rmtree(arch_lib_path)
def _ParseArchitecture(architectures):
- result = dict()
- for arch in architectures:
- if ":" in arch:
- target_environment, target_cpu = arch.split(":")
- else:
- logging.warning('The environment for build is not specified.')
- logging.warning('It is assumed based on cpu type.')
- logging.warning('See crbug.com/1138425 for more details.')
- if arch == "x64":
- target_environment = "simulator"
- else:
- target_environment = "device"
- target_cpu = arch
- archs = result.get(target_environment)
- if archs is None:
- result[target_environment] = {target_cpu}
- else:
- archs.add(target_cpu)
+ result = dict()
+ for arch in architectures:
+ if ":" in arch:
+ target_environment, target_cpu = arch.split(":")
+ else:
+ logging.warning('The environment for build is not specified.')
+ logging.warning('It is assumed based on cpu type.')
+ logging.warning('See crbug.com/1138425 for more details.')
+ if arch == "x64":
+ target_environment = "simulator"
+ else:
+ target_environment = "device"
+ target_cpu = arch
+ archs = result.get(target_environment)
+ if archs is None:
+ result[target_environment] = {target_cpu}
+ else:
+ archs.add(target_cpu)
- return result
+ return result
def BuildWebRTC(output_dir, target_environment, target_arch, flavor,
gn_target_name, ios_deployment_target, libvpx_build_vp9,
use_bitcode, use_goma, extra_gn_args):
- gn_args = [
- 'target_os="ios"', 'ios_enable_code_signing=false',
- 'is_component_build=false', 'rtc_include_tests=false',
- ]
+ gn_args = [
+ 'target_os="ios"',
+ 'ios_enable_code_signing=false',
+ 'is_component_build=false',
+ 'rtc_include_tests=false',
+ ]
- # Add flavor option.
- if flavor == 'debug':
- gn_args.append('is_debug=true')
- elif flavor == 'release':
- gn_args.append('is_debug=false')
- else:
- raise ValueError('Unexpected flavor type: %s' % flavor)
+ # Add flavor option.
+ if flavor == 'debug':
+ gn_args.append('is_debug=true')
+ elif flavor == 'release':
+ gn_args.append('is_debug=false')
+ else:
+ raise ValueError('Unexpected flavor type: %s' % flavor)
- gn_args.append('target_environment="%s"' % target_environment)
+ gn_args.append('target_environment="%s"' % target_environment)
- gn_args.append('target_cpu="%s"' % target_arch)
+ gn_args.append('target_cpu="%s"' % target_arch)
- gn_args.append('ios_deployment_target="%s"' % ios_deployment_target)
+ gn_args.append('ios_deployment_target="%s"' % ios_deployment_target)
- gn_args.append('rtc_libvpx_build_vp9=' +
- ('true' if libvpx_build_vp9 else 'false'))
+ gn_args.append('rtc_libvpx_build_vp9=' +
+ ('true' if libvpx_build_vp9 else 'false'))
- gn_args.append('enable_ios_bitcode=' +
- ('true' if use_bitcode else 'false'))
- gn_args.append('use_goma=' + ('true' if use_goma else 'false'))
- gn_args.append('rtc_enable_objc_symbol_export=true')
+ gn_args.append('enable_ios_bitcode=' + ('true' if use_bitcode else 'false'))
+ gn_args.append('use_goma=' + ('true' if use_goma else 'false'))
+ gn_args.append('rtc_enable_objc_symbol_export=true')
- args_string = ' '.join(gn_args + extra_gn_args)
- logging.info('Building WebRTC with args: %s', args_string)
+ args_string = ' '.join(gn_args + extra_gn_args)
+ logging.info('Building WebRTC with args: %s', args_string)
- cmd = [
- sys.executable,
- os.path.join(find_depot_tools.DEPOT_TOOLS_PATH, 'gn.py'),
- 'gen',
- output_dir,
- '--args=' + args_string,
- ]
- _RunCommand(cmd)
- logging.info('Building target: %s', gn_target_name)
+ cmd = [
+ sys.executable,
+ os.path.join(find_depot_tools.DEPOT_TOOLS_PATH, 'gn.py'),
+ 'gen',
+ output_dir,
+ '--args=' + args_string,
+ ]
+ _RunCommand(cmd)
+ logging.info('Building target: %s', gn_target_name)
- cmd = [
- os.path.join(find_depot_tools.DEPOT_TOOLS_PATH, 'ninja'),
- '-C',
- output_dir,
- gn_target_name,
- ]
- if use_goma:
- cmd.extend(['-j', '200'])
- _RunCommand(cmd)
+ cmd = [
+ os.path.join(find_depot_tools.DEPOT_TOOLS_PATH, 'ninja'),
+ '-C',
+ output_dir,
+ gn_target_name,
+ ]
+ if use_goma:
+ cmd.extend(['-j', '200'])
+ _RunCommand(cmd)
def main():
- args = _ParseArgs()
+ args = _ParseArgs()
- logging.basicConfig(level=logging.DEBUG if args.verbose else logging.INFO)
+ logging.basicConfig(level=logging.DEBUG if args.verbose else logging.INFO)
- if args.clean:
- _CleanArtifacts(args.output_dir)
- return 0
+ if args.clean:
+ _CleanArtifacts(args.output_dir)
+ return 0
- # architectures is typed as Dict[str, Set[str]],
- # where key is for the environment (device or simulator)
- # and value is for the cpu type.
- architectures = _ParseArchitecture(args.arch)
- gn_args = args.extra_gn_args
+ # architectures is typed as Dict[str, Set[str]],
+ # where key is for the environment (device or simulator)
+ # and value is for the cpu type.
+ architectures = _ParseArchitecture(args.arch)
+ gn_args = args.extra_gn_args
- if args.purify:
- _CleanTemporary(args.output_dir, architectures.keys())
- return 0
+ if args.purify:
+ _CleanTemporary(args.output_dir, list(architectures.keys()))
+ return 0
- gn_target_name = 'framework_objc'
- if not args.bitcode:
- gn_args.append('enable_dsyms=true')
- gn_args.append('enable_stripping=true')
+ gn_target_name = 'framework_objc'
+ if not args.bitcode:
+ gn_args.append('enable_dsyms=true')
+ gn_args.append('enable_stripping=true')
- # Build all architectures.
- framework_paths = []
- all_lib_paths = []
- for (environment, archs) in architectures.items():
- framework_path = os.path.join(args.output_dir, environment)
- framework_paths.append(framework_path)
- lib_paths = []
- for arch in archs:
- lib_path = os.path.join(framework_path, arch + '_libs')
- lib_paths.append(lib_path)
- BuildWebRTC(lib_path, environment, arch, args.build_config,
- gn_target_name, IOS_DEPLOYMENT_TARGET[environment],
- LIBVPX_BUILD_VP9, args.bitcode, args.use_goma, gn_args)
- all_lib_paths.extend(lib_paths)
+ # Build all architectures.
+ framework_paths = []
+ all_lib_paths = []
+ for (environment, archs) in list(architectures.items()):
+ framework_path = os.path.join(args.output_dir, environment)
+ framework_paths.append(framework_path)
+ lib_paths = []
+ for arch in archs:
+ lib_path = os.path.join(framework_path, arch + '_libs')
+ lib_paths.append(lib_path)
+ BuildWebRTC(lib_path, environment, arch, args.build_config,
+ gn_target_name, IOS_DEPLOYMENT_TARGET[environment],
+ LIBVPX_BUILD_VP9, args.bitcode, args.use_goma, gn_args)
+ all_lib_paths.extend(lib_paths)
- # Combine the slices.
- dylib_path = os.path.join(SDK_FRAMEWORK_NAME, 'WebRTC')
- # Dylibs will be combined, all other files are the same across archs.
- shutil.rmtree(
- os.path.join(framework_path, SDK_FRAMEWORK_NAME),
- ignore_errors=True)
- shutil.copytree(
- os.path.join(lib_paths[0], SDK_FRAMEWORK_NAME),
- os.path.join(framework_path, SDK_FRAMEWORK_NAME),
- symlinks=True)
- logging.info('Merging framework slices for %s.', environment)
- dylib_paths = [os.path.join(path, dylib_path) for path in lib_paths]
- out_dylib_path = os.path.join(framework_path, dylib_path)
- if os.path.islink(out_dylib_path):
- out_dylib_path = os.path.join(os.path.dirname(out_dylib_path),
- os.readlink(out_dylib_path))
- try:
- os.remove(out_dylib_path)
- except OSError:
- pass
- cmd = ['lipo'] + dylib_paths + ['-create', '-output', out_dylib_path]
- _RunCommand(cmd)
-
- # Merge the dSYM slices.
- lib_dsym_dir_path = os.path.join(lib_paths[0], SDK_DSYM_NAME)
- if os.path.isdir(lib_dsym_dir_path):
- shutil.rmtree(
- os.path.join(framework_path, SDK_DSYM_NAME),
- ignore_errors=True)
- shutil.copytree(
- lib_dsym_dir_path, os.path.join(framework_path, SDK_DSYM_NAME))
- logging.info('Merging dSYM slices.')
- dsym_path = os.path.join(SDK_DSYM_NAME, 'Contents', 'Resources',
- 'DWARF', 'WebRTC')
- lib_dsym_paths = [
- os.path.join(path, dsym_path) for path in lib_paths
- ]
- out_dsym_path = os.path.join(framework_path, dsym_path)
- try:
- os.remove(out_dsym_path)
- except OSError:
- pass
- cmd = ['lipo'
- ] + lib_dsym_paths + ['-create', '-output', out_dsym_path]
- _RunCommand(cmd)
-
- # Check for Mac-style WebRTC.framework/Resources/ (for Catalyst)...
- resources_dir = os.path.join(framework_path, SDK_FRAMEWORK_NAME,
- 'Resources')
- if not os.path.exists(resources_dir):
- # ...then fall back to iOS-style WebRTC.framework/
- resources_dir = os.path.dirname(resources_dir)
-
- # Modify the version number.
- # Format should be <Branch cut MXX>.<Hotfix #>.<Rev #>.
- # e.g. 55.0.14986 means
- # branch cut 55, no hotfixes, and revision 14986.
- infoplist_path = os.path.join(resources_dir, 'Info.plist')
- cmd = [
- 'PlistBuddy', '-c', 'Print :CFBundleShortVersionString',
- infoplist_path
- ]
- major_minor = subprocess.check_output(cmd).decode('utf-8').strip()
- version_number = '%s.%s' % (major_minor, args.revision)
- logging.info('Substituting revision number: %s', version_number)
- cmd = [
- 'PlistBuddy', '-c', 'Set :CFBundleVersion ' + version_number,
- infoplist_path
- ]
- _RunCommand(cmd)
- _RunCommand(['plutil', '-convert', 'binary1', infoplist_path])
-
- xcframework_dir = os.path.join(args.output_dir, SDK_XCFRAMEWORK_NAME)
- if os.path.isdir(xcframework_dir):
- shutil.rmtree(xcframework_dir)
-
- logging.info('Creating xcframework.')
- cmd = ['xcodebuild', '-create-xcframework', '-output', xcframework_dir]
-
- # Apparently, xcodebuild needs absolute paths for input arguments
- for framework_path in framework_paths:
- cmd += [
- '-framework',
- os.path.abspath(os.path.join(framework_path, SDK_FRAMEWORK_NAME)),
- ]
- dsym_full_path = os.path.join(framework_path, SDK_DSYM_NAME)
- if os.path.exists(dsym_full_path):
- cmd += ['-debug-symbols', os.path.abspath(dsym_full_path)]
-
+ # Combine the slices.
+ dylib_path = os.path.join(SDK_FRAMEWORK_NAME, 'WebRTC')
+ # Dylibs will be combined, all other files are the same across archs.
+ shutil.rmtree(os.path.join(framework_path, SDK_FRAMEWORK_NAME),
+ ignore_errors=True)
+ shutil.copytree(os.path.join(lib_paths[0], SDK_FRAMEWORK_NAME),
+ os.path.join(framework_path, SDK_FRAMEWORK_NAME),
+ symlinks=True)
+ logging.info('Merging framework slices for %s.', environment)
+ dylib_paths = [os.path.join(path, dylib_path) for path in lib_paths]
+ out_dylib_path = os.path.join(framework_path, dylib_path)
+ if os.path.islink(out_dylib_path):
+ out_dylib_path = os.path.join(os.path.dirname(out_dylib_path),
+ os.readlink(out_dylib_path))
+ try:
+ os.remove(out_dylib_path)
+ except OSError:
+ pass
+ cmd = ['lipo'] + dylib_paths + ['-create', '-output', out_dylib_path]
_RunCommand(cmd)
- # Generate the license file.
- logging.info('Generate license file.')
- gn_target_full_name = '//sdk:' + gn_target_name
- builder = LicenseBuilder(all_lib_paths, [gn_target_full_name])
- builder.GenerateLicenseText(
- os.path.join(args.output_dir, SDK_XCFRAMEWORK_NAME))
+ # Merge the dSYM slices.
+ lib_dsym_dir_path = os.path.join(lib_paths[0], SDK_DSYM_NAME)
+ if os.path.isdir(lib_dsym_dir_path):
+ shutil.rmtree(os.path.join(framework_path, SDK_DSYM_NAME),
+ ignore_errors=True)
+ shutil.copytree(lib_dsym_dir_path,
+ os.path.join(framework_path, SDK_DSYM_NAME))
+ logging.info('Merging dSYM slices.')
+ dsym_path = os.path.join(SDK_DSYM_NAME, 'Contents', 'Resources', 'DWARF',
+ 'WebRTC')
+ lib_dsym_paths = [os.path.join(path, dsym_path) for path in lib_paths]
+ out_dsym_path = os.path.join(framework_path, dsym_path)
+ try:
+ os.remove(out_dsym_path)
+ except OSError:
+ pass
+ cmd = ['lipo'] + lib_dsym_paths + ['-create', '-output', out_dsym_path]
+ _RunCommand(cmd)
- logging.info('Done.')
- return 0
+ # Check for Mac-style WebRTC.framework/Resources/ (for Catalyst)...
+ resources_dir = os.path.join(framework_path, SDK_FRAMEWORK_NAME,
+ 'Resources')
+ if not os.path.exists(resources_dir):
+ # ...then fall back to iOS-style WebRTC.framework/
+ resources_dir = os.path.dirname(resources_dir)
+
+ # Modify the version number.
+ # Format should be <Branch cut MXX>.<Hotfix #>.<Rev #>.
+ # e.g. 55.0.14986 means
+ # branch cut 55, no hotfixes, and revision 14986.
+ infoplist_path = os.path.join(resources_dir, 'Info.plist')
+ cmd = [
+ 'PlistBuddy', '-c', 'Print :CFBundleShortVersionString',
+ infoplist_path
+ ]
+ major_minor = subprocess.check_output(cmd).decode('utf-8').strip()
+ version_number = '%s.%s' % (major_minor, args.revision)
+ logging.info('Substituting revision number: %s', version_number)
+ cmd = [
+ 'PlistBuddy', '-c', 'Set :CFBundleVersion ' + version_number,
+ infoplist_path
+ ]
+ _RunCommand(cmd)
+ _RunCommand(['plutil', '-convert', 'binary1', infoplist_path])
+
+ xcframework_dir = os.path.join(args.output_dir, SDK_XCFRAMEWORK_NAME)
+ if os.path.isdir(xcframework_dir):
+ shutil.rmtree(xcframework_dir)
+
+ logging.info('Creating xcframework.')
+ cmd = ['xcodebuild', '-create-xcframework', '-output', xcframework_dir]
+
+ # Apparently, xcodebuild needs absolute paths for input arguments
+ for framework_path in framework_paths:
+ cmd += [
+ '-framework',
+ os.path.abspath(os.path.join(framework_path, SDK_FRAMEWORK_NAME)),
+ ]
+ dsym_full_path = os.path.join(framework_path, SDK_DSYM_NAME)
+ if os.path.exists(dsym_full_path):
+ cmd += ['-debug-symbols', os.path.abspath(dsym_full_path)]
+
+ _RunCommand(cmd)
+
+ # Generate the license file.
+ logging.info('Generate license file.')
+ gn_target_full_name = '//sdk:' + gn_target_name
+ builder = LicenseBuilder(all_lib_paths, [gn_target_full_name])
+ builder.GenerateLicenseText(
+ os.path.join(args.output_dir, SDK_XCFRAMEWORK_NAME))
+
+ logging.info('Done.')
+ return 0
if __name__ == '__main__':
- sys.exit(main())
+ sys.exit(main())