diff options
Diffstat (limited to 'third_party/libwebrtc/build/android/gyp/create_size_info_files.py')
-rwxr-xr-x | third_party/libwebrtc/build/android/gyp/create_size_info_files.py | 195 |
1 files changed, 195 insertions, 0 deletions
diff --git a/third_party/libwebrtc/build/android/gyp/create_size_info_files.py b/third_party/libwebrtc/build/android/gyp/create_size_info_files.py new file mode 100755 index 0000000000..c60b02d7c8 --- /dev/null +++ b/third_party/libwebrtc/build/android/gyp/create_size_info_files.py @@ -0,0 +1,195 @@ +#!/usr/bin/env python3 + +# Copyright 2018 The Chromium Authors. All rights reserved. +# Use of this source code is governed by a BSD-style license that can be +# found in the LICENSE file. + +"""Creates size-info/*.info files used by SuperSize.""" + +import argparse +import collections +import os +import re +import sys +import zipfile + +from util import build_utils +from util import jar_info_utils + + +_AAR_VERSION_PATTERN = re.compile(r'/[^/]*?(\.aar/|\.jar/)') + + +def _RemoveDuplicatesFromList(source_list): + return collections.OrderedDict.fromkeys(source_list).keys() + + +def _TransformAarPaths(path): + # .aar files within //third_party/android_deps have a version suffix. + # The suffix changes each time .aar files are updated, which makes size diffs + # hard to compare (since the before/after have different source paths). + # Rather than changing how android_deps works, we employ this work-around + # to normalize the paths. + # From: .../androidx_appcompat_appcompat/appcompat-1.1.0.aar/res/... + # To: .../androidx_appcompat_appcompat.aar/res/... + # https://crbug.com/1056455 + if 'android_deps' not in path: + return path + return _AAR_VERSION_PATTERN.sub(r'\1', path) + + +def _MergeResInfoFiles(res_info_path, info_paths): + # Concatenate them all. + # only_if_changed=False since no build rules depend on this as an input. + with build_utils.AtomicOutput(res_info_path, only_if_changed=False, + mode='w+') as dst: + for p in info_paths: + with open(p) as src: + dst.writelines(_TransformAarPaths(l) for l in src) + + +def _PakInfoPathsForAssets(assets): + return [f.split(':')[0] + '.info' for f in assets if f.endswith('.pak')] + + +def _MergePakInfoFiles(merged_path, pak_infos): + info_lines = set() + for pak_info_path in pak_infos: + with open(pak_info_path, 'r') as src_info_file: + info_lines.update(_TransformAarPaths(x) for x in src_info_file) + # only_if_changed=False since no build rules depend on this as an input. + with build_utils.AtomicOutput(merged_path, only_if_changed=False, + mode='w+') as f: + f.writelines(sorted(info_lines)) + + +def _FullJavaNameFromClassFilePath(path): + # Input: base/android/java/src/org/chromium/Foo.class + # Output: base.android.java.src.org.chromium.Foo + if not path.endswith('.class'): + return '' + path = os.path.splitext(path)[0] + parts = [] + while path: + # Use split to be platform independent. + head, tail = os.path.split(path) + path = head + parts.append(tail) + parts.reverse() # Package comes first + return '.'.join(parts) + + +def _MergeJarInfoFiles(output, inputs): + """Merge several .jar.info files to generate an .apk.jar.info. + + Args: + output: output file path. + inputs: List of .jar.info or .jar files. + """ + info_data = dict() + for path in inputs: + # For non-prebuilts: .jar.info files are written by compile_java.py and map + # .class files to .java source paths. + # + # For prebuilts: No .jar.info file exists, we scan the .jar files here and + # map .class files to the .jar. + # + # For .aar files: We look for a "source.info" file in the containing + # directory in order to map classes back to the .aar (rather than mapping + # them to the extracted .jar file). + if path.endswith('.info'): + info_data.update(jar_info_utils.ParseJarInfoFile(path)) + else: + attributed_path = path + if not path.startswith('..'): + parent_path = os.path.dirname(path) + # See if it's an sub-jar within the .aar. + if os.path.basename(parent_path) == 'libs': + parent_path = os.path.dirname(parent_path) + aar_source_info_path = os.path.join(parent_path, 'source.info') + # source.info files exist only for jars from android_aar_prebuilt(). + # E.g. Could have an java_prebuilt() pointing to a generated .jar. + if os.path.exists(aar_source_info_path): + attributed_path = jar_info_utils.ReadAarSourceInfo( + aar_source_info_path) + + with zipfile.ZipFile(path) as zip_info: + for name in zip_info.namelist(): + fully_qualified_name = _FullJavaNameFromClassFilePath(name) + if fully_qualified_name: + info_data[fully_qualified_name] = _TransformAarPaths('{}/{}'.format( + attributed_path, name)) + + # only_if_changed=False since no build rules depend on this as an input. + with build_utils.AtomicOutput(output, only_if_changed=False) as f: + jar_info_utils.WriteJarInfoFile(f, info_data) + + +def _FindJarInputs(jar_paths): + ret = [] + for jar_path in jar_paths: + jar_info_path = jar_path + '.info' + if os.path.exists(jar_info_path): + ret.append(jar_info_path) + else: + ret.append(jar_path) + return ret + + +def main(args): + args = build_utils.ExpandFileArgs(args) + parser = argparse.ArgumentParser(description=__doc__) + build_utils.AddDepfileOption(parser) + parser.add_argument( + '--jar-info-path', required=True, help='Output .jar.info file') + parser.add_argument( + '--pak-info-path', required=True, help='Output .pak.info file') + parser.add_argument( + '--res-info-path', required=True, help='Output .res.info file') + parser.add_argument( + '--jar-files', + required=True, + action='append', + help='GN-list of .jar file paths') + parser.add_argument( + '--assets', + required=True, + action='append', + help='GN-list of files to add as assets in the form ' + '"srcPath:zipPath", where ":zipPath" is optional.') + parser.add_argument( + '--uncompressed-assets', + required=True, + action='append', + help='Same as --assets, except disables compression.') + parser.add_argument( + '--in-res-info-path', + required=True, + action='append', + help='Paths to .ap_.info files') + + options = parser.parse_args(args) + + options.jar_files = build_utils.ParseGnList(options.jar_files) + options.assets = build_utils.ParseGnList(options.assets) + options.uncompressed_assets = build_utils.ParseGnList( + options.uncompressed_assets) + + jar_inputs = _FindJarInputs(_RemoveDuplicatesFromList(options.jar_files)) + pak_inputs = _PakInfoPathsForAssets(options.assets + + options.uncompressed_assets) + res_inputs = options.in_res_info_path + + # Just create the info files every time. See https://crbug.com/1045024 + _MergeJarInfoFiles(options.jar_info_path, jar_inputs) + _MergePakInfoFiles(options.pak_info_path, pak_inputs) + _MergeResInfoFiles(options.res_info_path, res_inputs) + + all_inputs = jar_inputs + pak_inputs + res_inputs + build_utils.WriteDepfile(options.depfile, + options.jar_info_path, + inputs=all_inputs) + + +if __name__ == '__main__': + main(sys.argv[1:]) |