| OLD | NEW |
| 1 # Copyright (c) 2013 Google Inc. All rights reserved. | 1 # Copyright (c) 2013 Google Inc. All rights reserved. |
| 2 # Use of this source code is governed by a BSD-style license that can be | 2 # Use of this source code is governed by a BSD-style license that can be |
| 3 # found in the LICENSE file. | 3 # found in the LICENSE file. |
| 4 | 4 |
| 5 import copy | 5 import copy |
| 6 import hashlib | 6 import hashlib |
| 7 import multiprocessing | 7 import multiprocessing |
| 8 import os.path | 8 import os.path |
| 9 import re | 9 import re |
| 10 import signal | 10 import signal |
| (...skipping 193 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 204 # - GypPathToNinja translates a gyp path (i.e. relative to the .gyp file) | 204 # - GypPathToNinja translates a gyp path (i.e. relative to the .gyp file) |
| 205 # into the equivalent ninja path. | 205 # into the equivalent ninja path. |
| 206 # | 206 # |
| 207 # - GypPathToUniqueOutput translates a gyp path into a ninja path to write | 207 # - GypPathToUniqueOutput translates a gyp path into a ninja path to write |
| 208 # an output file; the result can be namespaced such that it is unique | 208 # an output file; the result can be namespaced such that it is unique |
| 209 # to the input file name as well as the output target name. | 209 # to the input file name as well as the output target name. |
| 210 | 210 |
| 211 class NinjaWriter: | 211 class NinjaWriter: |
| 212 def __init__(self, qualified_target, target_outputs, base_dir, build_dir, | 212 def __init__(self, qualified_target, target_outputs, base_dir, build_dir, |
| 213 output_file, toplevel_build, output_file_name, flavor, | 213 output_file, toplevel_build, output_file_name, flavor, |
| 214 toplevel_dir=None): | 214 deps_file=None, toplevel_dir=None): |
| 215 """ | 215 """ |
| 216 base_dir: path from source root to directory containing this gyp file, | 216 base_dir: path from source root to directory containing this gyp file, |
| 217 by gyp semantics, all input paths are relative to this | 217 by gyp semantics, all input paths are relative to this |
| 218 build_dir: path from source root to build output | 218 build_dir: path from source root to build output |
| 219 toplevel_dir: path to the toplevel directory | 219 toplevel_dir: path to the toplevel directory |
| 220 """ | 220 """ |
| 221 | 221 |
| 222 self.qualified_target = qualified_target | 222 self.qualified_target = qualified_target |
| 223 self.target_outputs = target_outputs | 223 self.target_outputs = target_outputs |
| 224 self.base_dir = base_dir | 224 self.base_dir = base_dir |
| (...skipping 13 matching lines...) Expand all Loading... |
| 238 self.win_env = {} | 238 self.win_env = {} |
| 239 for arch in ('x86', 'x64'): | 239 for arch in ('x86', 'x64'): |
| 240 self.win_env[arch] = 'environment.' + arch | 240 self.win_env[arch] = 'environment.' + arch |
| 241 | 241 |
| 242 # Relative path from build output dir to base dir. | 242 # Relative path from build output dir to base dir. |
| 243 build_to_top = gyp.common.InvertRelativePath(build_dir, toplevel_dir) | 243 build_to_top = gyp.common.InvertRelativePath(build_dir, toplevel_dir) |
| 244 self.build_to_base = os.path.join(build_to_top, base_dir) | 244 self.build_to_base = os.path.join(build_to_top, base_dir) |
| 245 # Relative path from base dir to build dir. | 245 # Relative path from base dir to build dir. |
| 246 base_to_top = gyp.common.InvertRelativePath(base_dir, toplevel_dir) | 246 base_to_top = gyp.common.InvertRelativePath(base_dir, toplevel_dir) |
| 247 self.base_to_build = os.path.join(base_to_top, build_dir) | 247 self.base_to_build = os.path.join(base_to_top, build_dir) |
| 248 self.link_deps_file = deps_file |
| 248 | 249 |
| 249 def ExpandSpecial(self, path, product_dir=None): | 250 def ExpandSpecial(self, path, product_dir=None): |
| 250 """Expand specials like $!PRODUCT_DIR in |path|. | 251 """Expand specials like $!PRODUCT_DIR in |path|. |
| 251 | 252 |
| 252 If |product_dir| is None, assumes the cwd is already the product | 253 If |product_dir| is None, assumes the cwd is already the product |
| 253 dir. Otherwise, |product_dir| is the relative path to the product | 254 dir. Otherwise, |product_dir| is the relative path to the product |
| 254 dir. | 255 dir. |
| 255 """ | 256 """ |
| 256 | 257 |
| 257 PRODUCT_DIR = '$!PRODUCT_DIR' | 258 PRODUCT_DIR = '$!PRODUCT_DIR' |
| (...skipping 717 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 975 # - Linkable dependencies (like a .a or a .so): add them to the link line. | 976 # - Linkable dependencies (like a .a or a .so): add them to the link line. |
| 976 # - Non-linkable dependencies (like a rule that generates a file | 977 # - Non-linkable dependencies (like a rule that generates a file |
| 977 # and writes a stamp file): add them to implicit_deps | 978 # and writes a stamp file): add them to implicit_deps |
| 978 extra_link_deps = set() | 979 extra_link_deps = set() |
| 979 for dep in spec['dependencies']: | 980 for dep in spec['dependencies']: |
| 980 target = self.target_outputs.get(dep) | 981 target = self.target_outputs.get(dep) |
| 981 if not target: | 982 if not target: |
| 982 continue | 983 continue |
| 983 linkable = target.Linkable() | 984 linkable = target.Linkable() |
| 984 if linkable: | 985 if linkable: |
| 986 if self.link_deps_file: |
| 987 # Save the mapping of link deps. |
| 988 self.link_deps_file.write(self.qualified_target) |
| 989 self.link_deps_file.write(' ') |
| 990 self.link_deps_file.write(target.binary) |
| 991 self.link_deps_file.write('\n') |
| 992 |
| 985 if (self.flavor == 'win' and | 993 if (self.flavor == 'win' and |
| 986 target.component_objs and | 994 target.component_objs and |
| 987 self.msvs_settings.IsUseLibraryDependencyInputs(config_name)): | 995 self.msvs_settings.IsUseLibraryDependencyInputs(config_name)): |
| 988 extra_link_deps |= set(target.component_objs) | 996 extra_link_deps |= set(target.component_objs) |
| 989 elif self.flavor == 'win' and target.import_lib: | 997 elif self.flavor == 'win' and target.import_lib: |
| 990 extra_link_deps.add(target.import_lib) | 998 extra_link_deps.add(target.import_lib) |
| 991 elif target.UsesToc(self.flavor): | 999 elif target.UsesToc(self.flavor): |
| 992 solibs.add(target.binary) | 1000 solibs.add(target.binary) |
| 993 implicit_deps.add(target.binary + '.TOC') | 1001 implicit_deps.add(target.binary + '.TOC') |
| 994 else: | 1002 else: |
| (...skipping 1004 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1999 target_dicts, | 2007 target_dicts, |
| 2000 os.path.normpath(build_file)): | 2008 os.path.normpath(build_file)): |
| 2001 all_targets.add(target) | 2009 all_targets.add(target) |
| 2002 all_outputs = set() | 2010 all_outputs = set() |
| 2003 | 2011 |
| 2004 # target_outputs is a map from qualified target name to a Target object. | 2012 # target_outputs is a map from qualified target name to a Target object. |
| 2005 target_outputs = {} | 2013 target_outputs = {} |
| 2006 # target_short_names is a map from target short name to a list of Target | 2014 # target_short_names is a map from target short name to a list of Target |
| 2007 # objects. | 2015 # objects. |
| 2008 target_short_names = {} | 2016 target_short_names = {} |
| 2017 |
| 2018 # Extract the optional link deps file name. |
| 2019 LINK_DEPS_FILE = 'link_deps_file' |
| 2020 if LINK_DEPS_FILE in generator_flags: |
| 2021 link_deps_file = open(generator_flags.get(LINK_DEPS_FILE), 'wb') |
| 2022 else: |
| 2023 link_deps_file = None |
| 2024 |
| 2009 for qualified_target in target_list: | 2025 for qualified_target in target_list: |
| 2010 # qualified_target is like: third_party/icu/icu.gyp:icui18n#target | 2026 # qualified_target is like: third_party/icu/icu.gyp:icui18n#target |
| 2011 build_file, name, toolset = \ | 2027 build_file, name, toolset = \ |
| 2012 gyp.common.ParseQualifiedTarget(qualified_target) | 2028 gyp.common.ParseQualifiedTarget(qualified_target) |
| 2013 | 2029 |
| 2014 this_make_global_settings = data[build_file].get('make_global_settings', []) | 2030 this_make_global_settings = data[build_file].get('make_global_settings', []) |
| 2015 assert make_global_settings == this_make_global_settings, ( | 2031 assert make_global_settings == this_make_global_settings, ( |
| 2016 "make_global_settings needs to be the same for all targets.") | 2032 "make_global_settings needs to be the same for all targets.") |
| 2017 | 2033 |
| 2018 spec = target_dicts[qualified_target] | 2034 spec = target_dicts[qualified_target] |
| 2019 if flavor == 'mac': | 2035 if flavor == 'mac': |
| 2020 gyp.xcode_emulation.MergeGlobalXcodeSettingsToSpec(data[build_file], spec) | 2036 gyp.xcode_emulation.MergeGlobalXcodeSettingsToSpec(data[build_file], spec) |
| 2021 | 2037 |
| 2022 build_file = gyp.common.RelativePath(build_file, options.toplevel_dir) | 2038 build_file = gyp.common.RelativePath(build_file, options.toplevel_dir) |
| 2023 | 2039 |
| 2024 base_path = os.path.dirname(build_file) | 2040 base_path = os.path.dirname(build_file) |
| 2025 obj = 'obj' | 2041 obj = 'obj' |
| 2026 if toolset != 'target': | 2042 if toolset != 'target': |
| 2027 obj += '.' + toolset | 2043 obj += '.' + toolset |
| 2028 output_file = os.path.join(obj, base_path, name + '.ninja') | 2044 output_file = os.path.join(obj, base_path, name + '.ninja') |
| 2029 | 2045 |
| 2030 ninja_output = StringIO() | 2046 ninja_output = StringIO() |
| 2031 writer = NinjaWriter(qualified_target, target_outputs, base_path, build_dir, | 2047 writer = NinjaWriter(qualified_target, target_outputs, base_path, build_dir, |
| 2032 ninja_output, | 2048 ninja_output, |
| 2033 toplevel_build, output_file, | 2049 toplevel_build, output_file, |
| 2034 flavor, toplevel_dir=options.toplevel_dir) | 2050 flavor, link_deps_file, |
| 2051 toplevel_dir=options.toplevel_dir) |
| 2052 |
| 2035 target = writer.WriteSpec(spec, config_name, generator_flags) | 2053 target = writer.WriteSpec(spec, config_name, generator_flags) |
| 2036 | 2054 |
| 2037 if ninja_output.tell() > 0: | 2055 if ninja_output.tell() > 0: |
| 2038 # Only create files for ninja files that actually have contents. | 2056 # Only create files for ninja files that actually have contents. |
| 2039 with OpenOutput(os.path.join(toplevel_build, output_file)) as ninja_file: | 2057 with OpenOutput(os.path.join(toplevel_build, output_file)) as ninja_file: |
| 2040 ninja_file.write(ninja_output.getvalue()) | 2058 ninja_file.write(ninja_output.getvalue()) |
| 2041 ninja_output.close() | 2059 ninja_output.close() |
| 2042 master_ninja.subninja(output_file) | 2060 master_ninja.subninja(output_file) |
| 2043 | 2061 |
| 2044 if target: | 2062 if target: |
| (...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2102 arglists.append( | 2120 arglists.append( |
| 2103 (target_list, target_dicts, data, params, config_name)) | 2121 (target_list, target_dicts, data, params, config_name)) |
| 2104 pool.map(CallGenerateOutputForConfig, arglists) | 2122 pool.map(CallGenerateOutputForConfig, arglists) |
| 2105 except KeyboardInterrupt, e: | 2123 except KeyboardInterrupt, e: |
| 2106 pool.terminate() | 2124 pool.terminate() |
| 2107 raise e | 2125 raise e |
| 2108 else: | 2126 else: |
| 2109 for config_name in config_names: | 2127 for config_name in config_names: |
| 2110 GenerateOutputForConfig(target_list, target_dicts, data, params, | 2128 GenerateOutputForConfig(target_list, target_dicts, data, params, |
| 2111 config_name) | 2129 config_name) |
| OLD | NEW |