diff --git a/detect_host_arch.py b/detect_host_arch.py new file mode 100755 index 000000000..48b1539c4 --- /dev/null +++ b/detect_host_arch.py @@ -0,0 +1,51 @@ +#!/usr/bin/env python +# Copyright 2014 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. + +"""Outputs host CPU architecture in format recognized by gyp.""" + +import platform +import re +import sys + + +def HostArch(): + """Returns the host architecture with a predictable string.""" + host_arch = platform.machine() + + # Convert machine type to format recognized by gyp. + if re.match(r'i.86', host_arch) or host_arch == 'i86pc': + host_arch = 'x86' + elif host_arch in ['x86_64', 'amd64']: + host_arch = 'x64' + elif host_arch.startswith('arm'): + host_arch = 'arm' + elif host_arch.startswith('aarch64'): + host_arch = 'arm64' + elif host_arch.startswith('mips'): + host_arch = 'mips' + elif host_arch.startswith('ppc'): + host_arch = 'ppc' + elif host_arch.startswith('s390'): + host_arch = 's390' + + + # platform.machine is based on running kernel. It's possible to use 64-bit + # kernel with 32-bit userland, e.g. to give linker slightly more memory. + # Distinguish between different userland bitness by querying + # the python binary. + if host_arch == 'x64' and platform.architecture()[0] == '32bit': + host_arch = 'x86' + if host_arch == 'arm64' and platform.architecture()[0] == '32bit': + host_arch = 'arm' + + return host_arch + +def DoMain(_): + """Hook to be called from gyp without starting a separate python + interpreter.""" + return HostArch() + +if __name__ == '__main__': + print DoMain([]) diff --git a/gclient.py b/gclient.py index 9fe9ffa72..fe3388e37 100755 --- a/gclient.py +++ b/gclient.py @@ -75,6 +75,10 @@ # Example: # target_os = [ "ios" ] # target_os_only = True +# +# Specifying a target CPU +# To specify a target CPU, the variables target_cpu and target_cpu_only +# are available and are analagous to target_os and target_os_only. from __future__ import print_function @@ -94,6 +98,7 @@ import sys import time import urlparse +import detect_host_arch import fix_encoding import gclient_eval import gclient_scm @@ -348,6 +353,10 @@ class DependencySettings(object): else: return self.parent.target_os + @property + def target_cpu(self): + return self.parent.target_cpu + def get_custom_deps(self, name, url): """Returns a custom deps if applicable.""" if self.parent: @@ -1301,6 +1310,15 @@ class Dependency(gclient_utils.WorkItem, DependencySettings): 'checkout_mac': 'mac' in self.target_os, 'checkout_win': 'win' in self.target_os, 'host_os': _detect_host_os(), + + 'checkout_arm': 'arm' in self.target_cpu, + 'checkout_arm64': 'arm64' in self.target_cpu, + 'checkout_x86': 'x86' in self.target_cpu, + 'checkout_mips': 'mips' in self.target_cpu, + 'checkout_ppc': 'ppc' in self.target_cpu, + 'checkout_s390': 's390' in self.target_cpu, + 'checkout_x64': 'x64' in self.target_cpu, + 'host_cpu': detect_host_arch.HostArch(), } # Variables defined in DEPS file override built-in ones. result.update(self._vars) @@ -1384,6 +1402,7 @@ solutions = [ if 'all' in enforced_os: enforced_os = self.DEPS_OS_CHOICES.itervalues() self._enforced_os = tuple(set(enforced_os)) + self._enforced_cpu = detect_host_arch.HostArch(), self._root_dir = root_dir self.config_content = None @@ -1438,6 +1457,13 @@ it or fix the checkout. else: self._enforced_os = tuple(set(self._enforced_os).union(target_os)) + # Append any target CPU that is not already being enforced to the tuple. + target_cpu = config_dict.get('target_cpu', []) + if config_dict.get('target_cpu_only', False): + self._enforced_cpu = tuple(set(target_cpu)) + else: + self._enforced_cpu = tuple(set(self._enforced_cpu).union(target_cpu)) + cache_dir = config_dict.get('cache_dir', self._options.cache_dir) if cache_dir: cache_dir = os.path.join(self.root_dir, cache_dir) @@ -1450,6 +1476,10 @@ it or fix the checkout. raise gclient_utils.Error('Can\'t use target_os_only if target_os is ' 'not specified') + if not target_cpu and config_dict.get('target_cpu_only', False): + raise gclient_utils.Error('Can\'t use target_cpu_only if target_cpu is ' + 'not specified') + deps_to_add = [] for s in config_dict.get('solutions', []): try: @@ -1811,6 +1841,10 @@ it or fix the checkout. def target_os(self): return self._enforced_os + @property + def target_cpu(self): + return self._enforced_cpu + class GitDependency(Dependency): """A Dependency object that represents a single git checkout."""