• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1#!/usr/bin/env python
2
3import os
4import subprocess
5import sys
6
7SCRIPT_DIR = os.path.dirname(os.path.abspath(__file__))
8ANDROID_BUILD_TOP = os.path.abspath(os.path.join(SCRIPT_DIR, *(['..'] * 5)))
9
10NDK_VERSION = 'r11'
11API_LEVEL = 'android-24'
12
13def get_prebuilts_host():
14    if sys.platform.startswith('linux'):
15        return 'linux-x86'
16    if sys.platform.startswith('darwin'):
17        return 'darwin-x86'
18    raise NotImplementedError('unknown platform')
19
20def get_prebuilts_gcc(arch, gcc_version):
21    return os.path.join(ANDROID_BUILD_TOP, 'prebuilts', 'gcc',
22                        get_prebuilts_host(), arch, gcc_version)
23
24def get_prebuilts_clang():
25    return os.path.join(ANDROID_BUILD_TOP, 'prebuilts', 'clang', 'host',
26                        get_prebuilts_host(), 'clang-stable')
27
28def get_prebuilts_ndk(subdirs):
29    return os.path.join(ANDROID_BUILD_TOP, 'prebuilts', 'ndk', NDK_VERSION,
30                        'platforms', API_LEVEL, *subdirs)
31
32
33class Target(object):
34    def __init__(self, name, triple, cflags, ldflags, gcc_toolchain_dir,
35                 clang_dir, ndk_include, ndk_lib):
36        self.name = name
37        self.target_triple = triple
38        self.target_cflags = cflags
39        self.target_ldflags = ldflags
40
41        self.gcc_toolchain_dir = gcc_toolchain_dir
42        self.clang_dir = clang_dir
43        self.ndk_include = ndk_include
44        self.ndk_lib = ndk_lib
45
46    def compile(self, obj_file, src_file, cflags):
47        clang = os.path.join(self.clang_dir, 'bin', 'clang')
48
49        cmd = [clang, '-o', obj_file, '-c', src_file]
50        cmd.extend(['-fPIE', '-fPIC'])
51        cmd.extend(['-gcc-toolchain', self.gcc_toolchain_dir])
52        cmd.extend(['-target', self.target_triple])
53        cmd.extend(['-isystem', self.ndk_include])
54        cmd.extend(cflags)
55        cmd.extend(self.target_cflags)
56        subprocess.check_call(cmd)
57
58    def link(self, out_file, obj_files, ldflags):
59        if '-shared' in ldflags:
60            crtbegin = os.path.join(self.ndk_lib, 'crtbegin_so.o')
61            crtend = os.path.join(self.ndk_lib, 'crtend_so.o')
62        else:
63            crtbegin = os.path.join(self.ndk_lib, 'crtbegin_static.o')
64            crtend = os.path.join(self.ndk_lib, 'crtend_android.o')
65
66        clang = os.path.join(self.clang_dir, 'bin', 'clang')
67
68        cmd = [clang, '-o', out_file]
69        cmd.extend(['-fPIE', '-fPIC', '-Wl,--no-undefined', '-nostdlib'])
70        cmd.append('-L' + self.ndk_lib)
71        cmd.extend(['-gcc-toolchain', self.gcc_toolchain_dir])
72        cmd.extend(['-target', self.target_triple])
73        cmd.append(crtbegin)
74        cmd.extend(obj_files)
75        cmd.append(crtend)
76        cmd.extend(ldflags)
77        cmd.extend(self.target_ldflags)
78        if '-shared' not in ldflags:
79            cmd.append('-Wl,-pie')
80        subprocess.check_call(cmd)
81
82def create_targets():
83    return {
84        'arm': Target('arm', 'arm-linux-androideabi', [],[],
85            get_prebuilts_gcc('arm', 'arm-linux-androideabi-4.9'),
86            get_prebuilts_clang(),
87            get_prebuilts_ndk(['arch-arm', 'usr', 'include']),
88            get_prebuilts_ndk(['arch-arm', 'usr', 'lib'])),
89
90        'arm64': Target('arm64', 'aarch64-linux-android', [], [],
91            get_prebuilts_gcc('aarch64', 'aarch64-linux-android-4.9'),
92            get_prebuilts_clang(),
93            get_prebuilts_ndk(['arch-arm64', 'usr', 'include']),
94            get_prebuilts_ndk(['arch-arm64', 'usr', 'lib'])),
95
96        'x86': Target('x86', 'x86_64-linux-android', ['-m32'], ['-m32'],
97            get_prebuilts_gcc('x86', 'x86_64-linux-android-4.9'),
98            get_prebuilts_clang(),
99            get_prebuilts_ndk(['arch-x86', 'usr', 'include']),
100            get_prebuilts_ndk(['arch-x86', 'usr', 'lib'])),
101
102        'x86_64': Target('x86_64', 'x86_64-linux-android', ['-m64'], ['-m64'],
103            get_prebuilts_gcc('x86', 'x86_64-linux-android-4.9'),
104            get_prebuilts_clang(),
105            get_prebuilts_ndk(['arch-x86_64', 'usr', 'include']),
106            get_prebuilts_ndk(['arch-x86_64', 'usr', 'lib64'])),
107
108        'mips': Target('mips', 'mipsel-linux-android', [], [],
109            get_prebuilts_gcc('mips', 'mips64el-linux-android-4.9'),
110            get_prebuilts_clang(),
111            get_prebuilts_ndk(['arch-mips', 'usr', 'include']),
112            get_prebuilts_ndk(['arch-mips', 'usr', 'lib'])),
113
114        'mips64': Target('mips64', 'mips64el-linux-android',
115            ['-march=mips64el', '-mcpu=mips64r6'],
116            ['-march=mips64el', '-mcpu=mips64r6'],
117            get_prebuilts_gcc('mips', 'mips64el-linux-android-4.9'),
118            get_prebuilts_clang(),
119            get_prebuilts_ndk(['arch-mips64', 'usr', 'include']),
120            get_prebuilts_ndk(['arch-mips64', 'usr', 'lib64'])),
121    }
122