-
Notifications
You must be signed in to change notification settings - Fork 82
/
android.py
131 lines (109 loc) · 5.28 KB
/
android.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
"""Android SDK support"""
import os
import sys
if sys.version_info[0] >= 3:
from urllib.request import urlretrieve
else:
from urllib import urlretrieve
import zipfile
import subprocess
import hashlib
from mod import log, util
from mod.tools import java, javac
tools_urls = {
'win': 'https://dl.google.com/android/repository/sdk-tools-windows-3859397.zip',
'osx': 'https://dl.google.com/android/repository/sdk-tools-darwin-3859397.zip',
'linux': 'https://dl.google.com/android/repository/sdk-tools-linux-3859397.zip'
}
tools_archives = {
'win': 'sdk-tools-windows-3859397.zip',
'osx': 'sdk-tools-darwin-3859397.zip',
'linux': 'sdk-tools-linux-3859397.zip'
}
#-------------------------------------------------------------------------------
def get_sdk_dir(fips_dir) :
return util.get_workspace_dir(fips_dir) + '/fips-sdks/android'
#-------------------------------------------------------------------------------
def check_exists(fips_dir) :
"""check if the android sdk has been installed"""
return os.path.isdir(get_sdk_dir(fips_dir))
#-------------------------------------------------------------------------------
def get_adb_path(fips_dir):
return get_sdk_dir(fips_dir) + '/platform-tools/adb'
#-------------------------------------------------------------------------------
def get_tools_url() :
return tools_urls[util.get_host_platform()]
#-------------------------------------------------------------------------------
def get_tools_archive_path(fips_dir):
return get_sdk_dir(fips_dir) + '/' + tools_archives[util.get_host_platform()]
#-------------------------------------------------------------------------------
# convert a cmake target into a valid Android package name,
# some characters are invalid for package names and must be replaced
# NOTE: the same rules must be applied in the android-create-apk.py
# helper script which is run as a build job!
#
def target_to_package_name(target):
return 'org.fips.'+target.replace('-','_')
#-------------------------------------------------------------------------------
def install_package(fips_dir, pkg):
log.colored(log.BLUE, '>>> install Android SDK package: {}'.format(pkg))
sdkmgr_dir = get_sdk_dir(fips_dir) + '/tools/bin/'
sdkmgr_path = sdkmgr_dir + 'sdkmanager'
cmd = '{} --verbose {}'.format(sdkmgr_path, pkg)
subprocess.call(cmd, cwd=sdkmgr_dir, shell=True)
#-------------------------------------------------------------------------------
def ensure_sdk_dirs(fips_dir) :
if not os.path.isdir(get_sdk_dir(fips_dir)) :
os.makedirs(get_sdk_dir(fips_dir))
#-------------------------------------------------------------------------------
def uncompress(fips_dir, path) :
# the python zip module doesn't preserve the executable flags, so just
# call unzip on Linux and OSX
if util.get_host_platform() in ['osx', 'linux']:
subprocess.call('unzip {}'.format(path), cwd=get_sdk_dir(fips_dir), shell=True)
else:
with zipfile.ZipFile(path, 'r') as archive:
archive.extractall(get_sdk_dir(fips_dir))
#-------------------------------------------------------------------------------
def compute_sha256(path, converter=lambda x: x, chunk_size=65536) :
if not os.path.isfile(path) :
return None
result = hashlib.sha256()
with open(path, 'rb') as file :
chunk = file.read(chunk_size)
while chunk :
result.update(converter(chunk))
chunk = file.read(chunk_size)
return result.hexdigest()
#-------------------------------------------------------------------------------
def strip_whitespace(bin_str) :
for ws in [b' ', b'\t', b'\n', b'\r', b'\x0b', b'\x0c']:
bin_str = bin_str.replace(ws, b'')
return bin_str
#-------------------------------------------------------------------------------
def setup(fips_dir) :
"""setup the Android SDK and NDK"""
log.colored(log.YELLOW, '=== setup Android SDK/NDK :')
# first make sure that java is present, otherwise the Android
# SDK setup will finish without errors, but is not actually usable
if not java.check_exists(fips_dir) or not javac.check_exists(fips_dir) :
log.error("please install Java JDK 8 (see './fips diag tools')")
ensure_sdk_dirs(fips_dir)
# download the command line tools archive
tools_archive_path = get_tools_archive_path(fips_dir)
tools_url = get_tools_url()
log.info("downloading '{}'...".format(tools_url))
urlretrieve(tools_url, tools_archive_path, util.url_download_hook)
log.info("\nunpacking '{}'...".format(tools_archive_path))
uncompress(fips_dir, tools_archive_path)
# install the required SDK components through sdkmanager
install_package(fips_dir, '"platforms;android-28"')
install_package(fips_dir, '"build-tools;29.0.3"')
install_package(fips_dir, 'platform-tools')
install_package(fips_dir, 'ndk-bundle')
# check for potentially breaking changes in build setup
fips_cmake = fips_dir + '/cmake-toolchains/android.toolchain.orig'
ndk_cmake = get_sdk_dir(fips_dir) + '/ndk-bundle/build/cmake/android.toolchain.cmake'
if compute_sha256(ndk_cmake, strip_whitespace) != compute_sha256(fips_cmake, strip_whitespace) :
log.warn('android.toolchain.cmake in fips might be outdated...')
log.colored(log.GREEN, "done.")