| 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 json | 7 import json |
| 8 import multiprocessing | 8 import multiprocessing |
| 9 import os.path | 9 import os.path |
| 10 import re | 10 import re |
| (...skipping 1021 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1032 # linker flags are set via xcode_settings and msvs_settings, respectively. | 1032 # linker flags are set via xcode_settings and msvs_settings, respectively. |
| 1033 env_ldflags = os.environ.get('LDFLAGS', '').split() | 1033 env_ldflags = os.environ.get('LDFLAGS', '').split() |
| 1034 if self.flavor == 'mac': | 1034 if self.flavor == 'mac': |
| 1035 ldflags = self.xcode_settings.GetLdflags(config_name, | 1035 ldflags = self.xcode_settings.GetLdflags(config_name, |
| 1036 self.ExpandSpecial(generator_default_variables['PRODUCT_DIR']), | 1036 self.ExpandSpecial(generator_default_variables['PRODUCT_DIR']), |
| 1037 self.GypPathToNinja, arch) | 1037 self.GypPathToNinja, arch) |
| 1038 ldflags = env_ldflags + ldflags | 1038 ldflags = env_ldflags + ldflags |
| 1039 elif self.flavor == 'win': | 1039 elif self.flavor == 'win': |
| 1040 manifest_name = self.GypPathToUniqueOutput( | 1040 manifest_name = self.GypPathToUniqueOutput( |
| 1041 self.ComputeOutputFileName(spec)) | 1041 self.ComputeOutputFileName(spec)) |
| 1042 ldflags, manifest_files = self.msvs_settings.GetLdflags(config_name, | 1042 ldflags, intermediate_manifest, manifest_files = \ |
| 1043 self.GypPathToNinja, self.ExpandSpecial, manifest_name, is_executable) | 1043 self.msvs_settings.GetLdflags(config_name, self.GypPathToNinja, |
| 1044 self.ExpandSpecial, manifest_name, |
| 1045 is_executable, self.toplevel_build) |
| 1044 ldflags = env_ldflags + ldflags | 1046 ldflags = env_ldflags + ldflags |
| 1045 self.WriteVariableList(ninja_file, 'manifests', manifest_files) | 1047 self.WriteVariableList(ninja_file, 'manifests', manifest_files) |
| 1048 implicit_deps = implicit_deps.union(manifest_files) |
| 1049 if intermediate_manifest: |
| 1050 self.WriteVariableList( |
| 1051 ninja_file, 'intermediatemanifest', [intermediate_manifest]) |
| 1046 command_suffix = _GetWinLinkRuleNameSuffix( | 1052 command_suffix = _GetWinLinkRuleNameSuffix( |
| 1047 self.msvs_settings.IsEmbedManifest(config_name), | 1053 self.msvs_settings.IsEmbedManifest(config_name)) |
| 1048 self.msvs_settings.IsLinkIncremental(config_name)) | |
| 1049 def_file = self.msvs_settings.GetDefFile(self.GypPathToNinja) | 1054 def_file = self.msvs_settings.GetDefFile(self.GypPathToNinja) |
| 1050 if def_file: | 1055 if def_file: |
| 1051 implicit_deps.add(def_file) | 1056 implicit_deps.add(def_file) |
| 1052 else: | 1057 else: |
| 1053 # Respect environment variables related to build, but target-specific | 1058 # Respect environment variables related to build, but target-specific |
| 1054 # flags can still override them. | 1059 # flags can still override them. |
| 1055 ldflags = env_ldflags + config.get('ldflags', []) | 1060 ldflags = env_ldflags + config.get('ldflags', []) |
| 1056 if is_executable and len(solibs): | 1061 if is_executable and len(solibs): |
| 1057 rpath = 'lib/' | 1062 rpath = 'lib/' |
| 1058 if self.toolset != 'target': | 1063 if self.toolset != 'target': |
| (...skipping 439 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1498 | 1503 |
| 1499 global generator_filelist_paths | 1504 global generator_filelist_paths |
| 1500 generator_filelist_paths = { | 1505 generator_filelist_paths = { |
| 1501 'toplevel': toplevel, | 1506 'toplevel': toplevel, |
| 1502 'qualified_out_dir': qualified_out_dir, | 1507 'qualified_out_dir': qualified_out_dir, |
| 1503 } | 1508 } |
| 1504 | 1509 |
| 1505 | 1510 |
| 1506 def OpenOutput(path, mode='w'): | 1511 def OpenOutput(path, mode='w'): |
| 1507 """Open |path| for writing, creating directories if necessary.""" | 1512 """Open |path| for writing, creating directories if necessary.""" |
| 1508 try: | 1513 gyp.common.EnsureDirExists(path) |
| 1509 os.makedirs(os.path.dirname(path)) | |
| 1510 except OSError: | |
| 1511 pass | |
| 1512 return open(path, mode) | 1514 return open(path, mode) |
| 1513 | 1515 |
| 1514 | 1516 |
| 1515 def CommandWithWrapper(cmd, wrappers, prog): | 1517 def CommandWithWrapper(cmd, wrappers, prog): |
| 1516 wrapper = wrappers.get(cmd, '') | 1518 wrapper = wrappers.get(cmd, '') |
| 1517 if wrapper: | 1519 if wrapper: |
| 1518 return wrapper + ' ' + prog | 1520 return wrapper + ' ' + prog |
| 1519 return prog | 1521 return prog |
| 1520 | 1522 |
| 1521 | 1523 |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1560 # A static library debug build of Chromium's unit_tests takes ~2.7GB, so | 1562 # A static library debug build of Chromium's unit_tests takes ~2.7GB, so |
| 1561 # 4GB per ld process allows for some more bloat. | 1563 # 4GB per ld process allows for some more bloat. |
| 1562 return max(1, avail_bytes / (4 * (2 ** 30))) # total / 4GB | 1564 return max(1, avail_bytes / (4 * (2 ** 30))) # total / 4GB |
| 1563 except: | 1565 except: |
| 1564 return 1 | 1566 return 1 |
| 1565 else: | 1567 else: |
| 1566 # TODO(scottmg): Implement this for other platforms. | 1568 # TODO(scottmg): Implement this for other platforms. |
| 1567 return 1 | 1569 return 1 |
| 1568 | 1570 |
| 1569 | 1571 |
| 1570 def _GetWinLinkRuleNameSuffix(embed_manifest, link_incremental): | 1572 def _GetWinLinkRuleNameSuffix(embed_manifest): |
| 1571 """Returns the suffix used to select an appropriate linking rule depending on | 1573 """Returns the suffix used to select an appropriate linking rule depending on |
| 1572 whether the manifest embedding and/or incremental linking is enabled.""" | 1574 whether the manifest embedding is enabled.""" |
| 1573 suffix = '' | 1575 return '_embed' if embed_manifest else '' |
| 1574 if embed_manifest: | |
| 1575 suffix += '_embed' | |
| 1576 if link_incremental: | |
| 1577 suffix += '_inc' | |
| 1578 return suffix | |
| 1579 | 1576 |
| 1580 | 1577 |
| 1581 def _AddWinLinkRules(master_ninja, embed_manifest, link_incremental): | 1578 def _AddWinLinkRules(master_ninja, embed_manifest): |
| 1582 """Adds link rules for Windows platform to |master_ninja|.""" | 1579 """Adds link rules for Windows platform to |master_ninja|.""" |
| 1583 def FullLinkCommand(ldcmd, out, binary_type): | 1580 def FullLinkCommand(ldcmd, out, binary_type): |
| 1584 """Returns a one-liner written for cmd.exe to handle multiphase linker | |
| 1585 operations including manifest file generation. The command will be | |
| 1586 structured as follows: | |
| 1587 cmd /c (linkcmd1 a b) && (linkcmd2 x y) && ... && | |
| 1588 if not "$manifests"=="" ((manifestcmd1 a b) && (manifestcmd2 x y) && ... ) | |
| 1589 Note that $manifests becomes empty when no manifest file is generated.""" | |
| 1590 link_commands = ['%(ldcmd)s', | |
| 1591 'if exist %(out)s.manifest del %(out)s.manifest'] | |
| 1592 mt_cmd = ('%(python)s gyp-win-tool manifest-wrapper' | |
| 1593 ' $arch $mt -nologo -manifest $manifests') | |
| 1594 if embed_manifest and not link_incremental: | |
| 1595 # Embed manifest into a binary. If incremental linking is enabled, | |
| 1596 # embedding is postponed to the re-linking stage (see below). | |
| 1597 mt_cmd += ' -outputresource:%(out)s;%(resname)s' | |
| 1598 else: | |
| 1599 # Save manifest as an external file. | |
| 1600 mt_cmd += ' -out:%(out)s.manifest' | |
| 1601 manifest_commands = [mt_cmd] | |
| 1602 if link_incremental: | |
| 1603 # There is no point in generating separate rule for the case when | |
| 1604 # incremental linking is enabled, but manifest embedding is disabled. | |
| 1605 # In that case the basic rule should be used (e.g. 'link'). | |
| 1606 # See also implementation of _GetWinLinkRuleNameSuffix(). | |
| 1607 assert embed_manifest | |
| 1608 # Make .rc file out of manifest, compile it to .res file and re-link. | |
| 1609 manifest_commands += [ | |
| 1610 ('%(python)s gyp-win-tool manifest-to-rc $arch %(out)s.manifest' | |
| 1611 ' %(out)s.manifest.rc %(resname)s'), | |
| 1612 '%(python)s gyp-win-tool rc-wrapper $arch $rc %(out)s.manifest.rc', | |
| 1613 '%(ldcmd)s %(out)s.manifest.res'] | |
| 1614 cmd = 'cmd /c %s && if not "$manifests"=="" (%s)' % ( | |
| 1615 ' && '.join(['(%s)' % c for c in link_commands]), | |
| 1616 ' && '.join(['(%s)' % c for c in manifest_commands])) | |
| 1617 resource_name = { | 1581 resource_name = { |
| 1618 'exe': '1', | 1582 'exe': '1', |
| 1619 'dll': '2', | 1583 'dll': '2', |
| 1620 }[binary_type] | 1584 }[binary_type] |
| 1621 return cmd % {'python': sys.executable, | 1585 return '%(python)s gyp-win-tool link-with-manifests $arch %(embed)s ' \ |
| 1622 'out': out, | 1586 '%(out)s "%(ldcmd)s" %(resname)s $mt $rc "$intermediatemanifest" ' \ |
| 1623 'ldcmd': ldcmd, | 1587 '$manifests' % { |
| 1624 'resname': resource_name} | 1588 'python': sys.executable, |
| 1625 | 1589 'out': out, |
| 1626 rule_name_suffix = _GetWinLinkRuleNameSuffix(embed_manifest, link_incremental) | 1590 'ldcmd': ldcmd, |
| 1591 'resname': resource_name, |
| 1592 'embed': embed_manifest } |
| 1593 rule_name_suffix = _GetWinLinkRuleNameSuffix(embed_manifest) |
| 1627 dlldesc = 'LINK%s(DLL) $dll' % rule_name_suffix.upper() | 1594 dlldesc = 'LINK%s(DLL) $dll' % rule_name_suffix.upper() |
| 1628 dllcmd = ('%s gyp-win-tool link-wrapper $arch ' | 1595 dllcmd = ('%s gyp-win-tool link-wrapper $arch ' |
| 1629 '$ld /nologo $implibflag /DLL /OUT:$dll ' | 1596 '$ld /nologo $implibflag /DLL /OUT:$dll ' |
| 1630 '/PDB:$dll.pdb @$dll.rsp' % sys.executable) | 1597 '/PDB:$dll.pdb @$dll.rsp' % sys.executable) |
| 1631 dllcmd = FullLinkCommand(dllcmd, '$dll', 'dll') | 1598 dllcmd = FullLinkCommand(dllcmd, '$dll', 'dll') |
| 1632 master_ninja.rule('solink' + rule_name_suffix, | 1599 master_ninja.rule('solink' + rule_name_suffix, |
| 1633 description=dlldesc, command=dllcmd, | 1600 description=dlldesc, command=dllcmd, |
| 1634 rspfile='$dll.rsp', | 1601 rspfile='$dll.rsp', |
| 1635 rspfile_content='$libs $in_newline $ldflags', | 1602 rspfile_content='$libs $in_newline $ldflags', |
| 1636 restat=True, | 1603 restat=True, |
| (...skipping 271 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1908 pool='link_pool') | 1875 pool='link_pool') |
| 1909 elif flavor == 'win': | 1876 elif flavor == 'win': |
| 1910 master_ninja.rule( | 1877 master_ninja.rule( |
| 1911 'alink', | 1878 'alink', |
| 1912 description='LIB $out', | 1879 description='LIB $out', |
| 1913 command=('%s gyp-win-tool link-wrapper $arch ' | 1880 command=('%s gyp-win-tool link-wrapper $arch ' |
| 1914 '$ar /nologo /ignore:4221 /OUT:$out @$out.rsp' % | 1881 '$ar /nologo /ignore:4221 /OUT:$out @$out.rsp' % |
| 1915 sys.executable), | 1882 sys.executable), |
| 1916 rspfile='$out.rsp', | 1883 rspfile='$out.rsp', |
| 1917 rspfile_content='$in_newline $libflags') | 1884 rspfile_content='$in_newline $libflags') |
| 1918 _AddWinLinkRules(master_ninja, embed_manifest=True, link_incremental=True) | 1885 _AddWinLinkRules(master_ninja, embed_manifest=True) |
| 1919 _AddWinLinkRules(master_ninja, embed_manifest=True, link_incremental=False) | 1886 _AddWinLinkRules(master_ninja, embed_manifest=False) |
| 1920 _AddWinLinkRules(master_ninja, embed_manifest=False, link_incremental=False) | |
| 1921 # Do not generate rules for embed_manifest=False and link_incremental=True | |
| 1922 # because in that case rules for (False, False) should be used (see | |
| 1923 # implementation of _GetWinLinkRuleNameSuffix()). | |
| 1924 else: | 1887 else: |
| 1925 master_ninja.rule( | 1888 master_ninja.rule( |
| 1926 'objc', | 1889 'objc', |
| 1927 description='OBJC $out', | 1890 description='OBJC $out', |
| 1928 command=('$cc -MMD -MF $out.d $defines $includes $cflags $cflags_objc ' | 1891 command=('$cc -MMD -MF $out.d $defines $includes $cflags $cflags_objc ' |
| 1929 '$cflags_pch_objc -c $in -o $out'), | 1892 '$cflags_pch_objc -c $in -o $out'), |
| 1930 depfile='$out.d', | 1893 depfile='$out.d', |
| 1931 deps=deps) | 1894 deps=deps) |
| 1932 master_ninja.rule( | 1895 master_ninja.rule( |
| 1933 'objcxx', | 1896 'objcxx', |
| (...skipping 226 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2160 arglists.append( | 2123 arglists.append( |
| 2161 (target_list, target_dicts, data, params, config_name)) | 2124 (target_list, target_dicts, data, params, config_name)) |
| 2162 pool.map(CallGenerateOutputForConfig, arglists) | 2125 pool.map(CallGenerateOutputForConfig, arglists) |
| 2163 except KeyboardInterrupt, e: | 2126 except KeyboardInterrupt, e: |
| 2164 pool.terminate() | 2127 pool.terminate() |
| 2165 raise e | 2128 raise e |
| 2166 else: | 2129 else: |
| 2167 for config_name in config_names: | 2130 for config_name in config_names: |
| 2168 GenerateOutputForConfig(target_list, target_dicts, data, params, | 2131 GenerateOutputForConfig(target_list, target_dicts, data, params, |
| 2169 config_name) | 2132 config_name) |
| OLD | NEW |