cmake/install-share.py: refactor code and its usage in CMake.

This commit is contained in:
Peter Matula 2018-07-18 15:27:50 +02:00
parent 2275495d2a
commit 0938102924
5 changed files with 90 additions and 111 deletions

View File

@ -16,6 +16,14 @@ set(CMAKE_CXX_STANDARD 14)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
set(CMAKE_CXX_EXTENSIONS OFF)
# RetDec, and some dependencies (e.g. LLVM, Keystone), require python3, so we
# first check whether python3 is installed as "python3", and if not, we suppose
# that `python` runs python3.
find_program(PYTHON3_EXECUTABLE "python3")
if(NOT PYTHON3_EXECUTABLE)
find_program(PYTHON3_EXECUTABLE "python")
endif()
function(append_if condition value)
if (${condition})
foreach(variable ${ARGN})

View File

@ -1,16 +1,9 @@
install(CODE "
if (WIN32)
execute_process(
COMMAND py -3 \"${CMAKE_SOURCE_DIR}/cmake/install-share.py\" \"${CMAKE_INSTALL_PREFIX}\"
RESULT_VARIABLE INSTALL_SHARE_RES
)
else()
execute_process(
COMMAND python3 \"${CMAKE_SOURCE_DIR}/cmake/install-share.py\" \"${CMAKE_INSTALL_PREFIX}\"
RESULT_VARIABLE INSTALL_SHARE_RES
)
endif()
execute_process(
# -u = unbuffered -> print debug messages right away.
COMMAND ${PYTHON3_EXECUTABLE} -u \"${CMAKE_SOURCE_DIR}/cmake/install-share.py\" \"${CMAKE_INSTALL_PREFIX}\"
RESULT_VARIABLE INSTALL_SHARE_RES
)
if(INSTALL_SHARE_RES)
message(FATAL_ERROR \"RetDec share directory installation FAILED\")
endif()

View File

@ -10,11 +10,6 @@ import shutil
import tarfile
import urllib.request
# Check arguments.
if len(sys.argv) != 2:
print('ERROR: Unexpected number of arguments.')
sys.exit(1)
###############################################################################
version_filename = 'version.txt'
@ -23,93 +18,91 @@ arch_suffix = 'tar.xz'
sha256hash_ref = 'b54ba07e2f28143c9afe34a9d5b4114fb61f3c1175b9807caced471fec82001e'
version = '2018-02-08'
###############################################################################
arch_name = 'retdec-support' + '_' + version + '.' + arch_suffix
# Get install path from script options.
install_path = sys.argv[1]
share_dir = os.path.join(install_path, 'share')
share_retdec_dir = os.path.join(share_dir, 'retdec')
support_dir = os.path.join(share_retdec_dir, 'support')
arch_path = os.path.join(support_dir, arch_name)
###############################################################################
def cleanup():
def cleanup(support_dir):
shutil.rmtree(support_dir, ignore_errors=True)
def get_install_path(argv):
if len(argv) != 2:
print('ERROR: Unexpected number of arguments.')
sys.exit(1)
else:
return argv[1]
def main():
install_path = get_install_path(sys.argv)
support_dir = os.path.join(install_path, 'share', 'retdec', 'support')
arch_path = os.path.join(support_dir, arch_name)
# Share directory exists.
if os.path.exists(support_dir):
for n in os.listdir(support_dir):
p = os.path.join(support_dir, n)
if os.path.isdir(p):
shutil.rmtree(p)
version_path = os.path.join(support_dir, version_filename)
if os.path.isfile(version_path):
with open(version_path) as version_file:
version_from_file = version_file.read().split('\n')[0]
if version == version_from_file:
print('%s already exists, version is ok' % support_dir)
sys.exit(0)
else:
os.unlink(p)
print('versions is not as expected -> replace with the expected version')
cleanup(support_dir)
# Make sure destination directory exists.
os.makedirs(support_dir, exist_ok=True)
# Share directory exists.
if os.path.exists(support_dir):
# Version file exists.
if os.path.isfile(os.path.join(support_dir, version_filename)):
with open(os.path.join(support_dir, version_filename)) as version_file:
version_from_file = version_file.read().split('\n')[0]
# Download archive
arch_url = 'https://github.com/avast-tl/retdec-support/releases/download/%s/%s' % (version, arch_name)
print('Downloading archive from %s ...' % arch_url)
if version == version_from_file:
print('%s already exists, version is ok' % support_dir)
sys.exit(0)
else:
print('versions is not as expected -> replace with expected version')
cleanup()
# Make sure destination directory exists.
os.makedirs(support_dir, exist_ok=True)
# Download archive
arch_url = 'https://github.com/avast-tl/retdec-support/releases/download/%s/%s' % (version, arch_name)
print('Downloading archive from %s ...' % arch_url)
try:
urllib.request.urlretrieve(arch_url, arch_path)
except (urllib.request.HTTPError, urllib.request.URLError):
print('ERROR: download failed')
cleanup()
sys.exit(1)
# Compute hash of the downloaded archive.
print('Verfifying archive\'s checksum ...')
sha256 = hashlib.sha256()
with open(arch_path, 'rb') as f:
try:
sha256.update(f.read())
except IOError:
print('ERROR: failed to compute the SHA-256 hash of the archive')
cleanup()
urllib.request.urlretrieve(arch_url, arch_path)
except (urllib.request.HTTPError, urllib.request.URLError):
print('ERROR: download failed')
cleanup(support_dir)
sys.exit(1)
sha256hash = sha256.hexdigest()
# Compute hash of the downloaded archive.
print('Verfifying archive\'s checksum ...')
# Check that hash is ok.
if sha256hash != sha256hash_ref:
print('ERROR: downloaded archive is invalid (SHA-256 hash check failed)')
cleanup()
sys.exit(1)
sha256 = hashlib.sha256()
with open(arch_path, 'rb') as f:
try:
sha256.update(f.read())
except IOError:
print('ERROR: failed to compute the SHA-256 hash of the archive')
cleanup(support_dir)
sys.exit(1)
# Unpack archive.
print('Unpacking archive ...')
with tarfile.open(arch_path) as tar:
try:
tar.extractall(support_dir)
except tarfile.ExtractError:
print('ERROR: failed to unpack the archive')
cleanup()
sha256hash = sha256.hexdigest()
# Check that hash is ok.
if sha256hash != sha256hash_ref:
print('ERROR: downloaded archive is invalid (SHA-256 hash check failed)')
cleanup(support_dir)
sys.exit(1)
# Remove archive.
os.remove(arch_path)
# Unpack archive.
print('Unpacking archive ...')
with tarfile.open(arch_path) as tar:
try:
tar.extractall(support_dir)
except tarfile.ExtractError:
print('ERROR: failed to unpack the archive')
cleanup(support_dir)
sys.exit(1)
print('RetDec support directory downloaded OK')
sys.exit(0)
# Remove archive.
os.remove(arch_path)
print('RetDec support directory downloaded OK')
sys.exit(0)
if __name__ == "__main__":
main()

View File

@ -7,15 +7,6 @@ if(CMAKE_CXX_COMPILER)
set(CMAKE_CXX_COMPILER_OPTION "-DCMAKE_CXX_COMPILER=${CMAKE_CXX_COMPILER}")
endif()
# Keystone requires python3, so we first check whether python3 is installed as
# "python3", and if not, we suppose that `python` runs python3.
# Python is used to generate LLVMBuild.cmake file. Python2 generates this file
# with UNIX paths, which do not work. Python3 generates proper Windows paths.
find_program(PYTHON_EXECUTABLE "python3")
if(NOT PYTHON_EXECUTABLE)
find_program(PYTHON_EXECUTABLE "python")
endif()
ExternalProject_Add(keystone-project
URL https://github.com/keystone-engine/keystone/archive/d7ba8e378e5284e6384fc9ecd660ed5f6532e922.zip
URL_HASH SHA256=13bd00e062e9c778fe76aaab5c163348b3c9457c0e9b2a4c2fb3e2d8747694ca
@ -23,8 +14,10 @@ ExternalProject_Add(keystone-project
CMAKE_ARGS
# This does not work on MSVC, but may be useful on Linux.
-DCMAKE_BUILD_TYPE=Release
# Force python version set in this cmake file.
-DPYTHON_EXECUTABLE=${PYTHON_EXECUTABLE}
# Force python3 version set in this cmake file.
# Python is used to generate LLVMBuild.cmake file. Python2 generates this file
# with UNIX paths, which do not work. Python3 generates proper Windows paths.
-DPYTHON_EXECUTABLE=${PYTHON3_EXECUTABLE}
-DKEYSTONE_BUILD_STATIC_RUNTIME=OFF
# Force the use of the same compiler as used to build the top-level
# project. Otherwise, the external project may pick up a different

View File

@ -27,13 +27,6 @@ endif()
# install only some tools from LLVM, not all the libraries and tools.
include(ExternalProject)
# LLVM requires python3, so we first check whether python3 is installed as
# "python3", and if not, we suppose that `python` runs python3.
find_program(PYTHON_EXECUTABLE "python3")
if(NOT PYTHON_EXECUTABLE)
find_program(PYTHON_EXECUTABLE "python")
endif()
ExternalProject_Add(llvm-project
URL https://github.com/avast-tl/llvm/archive/725d0cee133c6ab9b95c493f05de3b08016f5c3c.zip
URL_HASH SHA256=0ec70e790a84df1dcc4e5bb30f9a3ae32eb280aad8a4711158ba227513ddebf4
@ -43,9 +36,8 @@ ExternalProject_Add(llvm-project
# This has no effect on Windows with MSVC, but is useful on Linux.
-DCMAKE_BUILD_TYPE=Release
# Force Python3 (see the comment above when setting
# PYTHON_EXECUTABLE).
-DPYTHON_EXECUTABLE=${PYTHON_EXECUTABLE}
# Force Python3 (see the comment when setting PYTHON3_EXECUTABLE).
-DPYTHON_EXECUTABLE=${PYTHON3_EXECUTABLE}
# Targets to be build.
-DLLVM_TARGETS_TO_BUILD=X86