diff --git a/.circleci/config.yml b/.circleci/config.yml deleted file mode 100644 index 00fae5351..000000000 --- a/.circleci/config.yml +++ /dev/null @@ -1,217 +0,0 @@ -version: 2.1 - -orbs: - win: circleci/windows@2.4 - -jobs: - build-test-python: - parameters: - python_version: - description: "Python version specified as X.Y.Z" - type: string - python_arch: - description: "Python arch specified as x64 or x86" - type: string - working_directory: /work - docker: - - image: dockcross/linux-<< parameters.python_arch >> - steps: - - checkout - - run: - name: Install Dependencies - command: | - sudo apt-get update - sudo apt-get install -y \ - libbz2-dev \ - libdb-dev \ - libffi-dev \ - libgdbm-compat-dev \ - libgdbm-dev \ - liblzma-dev \ - libncursesw5-dev \ - libreadline-dev \ - libsqlite3-dev \ - libssl-dev \ - tcl-dev \ - tk-dev - - run: - name: download dashboard scripts - command: | - git clone git@github.com:python-cmake-buildsystem/python-cmake-buildsystem --branch dashboard --depth 1 scripts - - run: - name: build and test - command: | - set -e - ctest --timeout 360 -S /work/scripts/circle_dashboard.cmake -VV - environment: - PY_VERSION: << parameters.python_version >> - - build-test-python-win: - parameters: - python_version: - description: "Python version specified as X.Y.Z" - type: string - python_arch: - description: "Python arch specified as x64 or Win32" - type: string - generator: - description: "CMake generator" - type: string - executor: - name: win/default - shell: powershell.exe - working_directory: C:/Users/circleci/project/src - steps: - - checkout - - run: - name: Install dependencies - command: | - choco install --no-progress cmake - if (-not $?) { throw "Failed to install CMake" } - - run: - name: download dashboard scripts - command: | - git clone git@github.com:python-cmake-buildsystem/python-cmake-buildsystem --branch dashboard --depth 1 ../scripts - - run: - name: build and test - command: | - $Env:PATH += ";C:\Program Files\CMake\bin" - ctest -C $Env:CONFIGURATION -S C:/Users/circleci/project/scripts/circle_win_dashboard.cmake -VV - environment: - PY_VERSION: << parameters.python_version >> - CONFIGURATION: Release - GENERATOR: << parameters.generator >> - PLATFORM: << parameters.python_arch >> - -workflows: - build-and-test: - jobs: - # 3.12.10 - - build-test-python: - name: python-3.12.10-x64 - python_version: 3.12.10 - python_arch: x64 - - - build-test-python: - name: python-3.12.10-x86 - python_version: 3.12.10 - python_arch: x86 - - # 3.11.12 - - build-test-python: - name: python-3.11.12-x64 - python_version: 3.11.12 - python_arch: x64 - - - build-test-python: - name: python-3.11.12-x86 - python_version: 3.11.12 - python_arch: x86 - - # 3.10.17 - - build-test-python: - name: python-3.10.17-x64 - python_version: 3.10.17 - python_arch: x64 - - - build-test-python: - name: python-3.10.17-x86 - python_version: 3.10.17 - python_arch: x86 - - # 3.9.22 - - build-test-python: - name: python-3.9.22-x64 - python_version: 3.9.22 - python_arch: x64 - - - build-test-python: - name: python-3.9.22-x86 - python_version: 3.9.22 - python_arch: x86 - - # 3.8.20 - - build-test-python: - name: python-3.8.20-x64 - python_version: 3.8.20 - python_arch: x64 - - - build-test-python: - name: python-3.8.20-x86 - python_version: 3.8.20 - python_arch: x86 - - # 3.7.17 - - build-test-python: - name: python-3.7.17-x64 - python_version: 3.7.17 - python_arch: x64 - - - build-test-python: - name: python-3.7.17-x86 - python_version: 3.7.17 - python_arch: x86 - - # 3.6.15 - - build-test-python: - name: python-3.6.15-x64 - python_version: 3.6.15 - python_arch: x64 - - - build-test-python: - name: python-3.6.15-x86 - python_version: 3.6.15 - python_arch: x86 - - - build-and-test-win: - jobs: - # 3.12.10 - - build-test-python-win: - name: python-3.12.10-win-x64 - python_version: 3.12.10 - python_arch: x64 - generator: "Visual Studio 16 2019" - - # 3.11.12 - - build-test-python-win: - name: python-3.11.12-win-x64 - python_version: 3.11.12 - python_arch: x64 - generator: "Visual Studio 16 2019" - - # 3.10.17 - - build-test-python-win: - name: python-3.10.17-win-x64 - python_version: 3.10.17 - python_arch: x64 - generator: "Visual Studio 16 2019" - - # 3.9.22 - - build-test-python-win: - name: python-3.9.22-win-x64 - python_version: 3.9.22 - python_arch: x64 - generator: "Visual Studio 16 2019" - - # 3.8.20 - - build-test-python-win: - name: python-3.8.20-win-x64 - python_version: 3.8.20 - python_arch: x64 - generator: "Visual Studio 16 2019" - - # 3.7.17 - - build-test-python-win: - name: python-3.7.17-win-x64 - python_version: 3.7.17 - python_arch: x64 - generator: "Visual Studio 16 2019" - - # 3.6.15 - - build-test-python-win: - name: python-3.6.15-win-x64 - python_version: 3.6.15 - python_arch: x64 - generator: "Visual Studio 16 2019" - diff --git a/.github/dashboard/.gitignore b/.github/dashboard/.gitignore new file mode 100644 index 000000000..e8eeb5120 --- /dev/null +++ b/.github/dashboard/.gitignore @@ -0,0 +1 @@ +initial-dashboard-cache.txt diff --git a/.github/dashboard/circle_dashboard.cmake b/.github/dashboard/circle_dashboard.cmake new file mode 100644 index 000000000..f7d0dfc94 --- /dev/null +++ b/.github/dashboard/circle_dashboard.cmake @@ -0,0 +1,60 @@ +# Client maintainer: jchris.fillionr@kitware.com + +# Sanity checks +foreach(name IN ITEMS + DEFAULT_DOCKCROSS_IMAGE + PY_VERSION + ) + if("$ENV{${name}}" STREQUAL "") + message(FATAL_ERROR "Environment variable '${name}' is not set") + endif() +endforeach() + +# Extract major/minor/patch python versions +set(PY_VERSION $ENV{PY_VERSION}) +string(REGEX MATCH "([0-9])\\.([0-9]+)\\.([0-9]+)" _match ${PY_VERSION}) +if(_match STREQUAL "") + message(FATAL_ERROR "Environment variable 'PY_VERSION' is improperly set.") +endif() + +set(CTEST_SITE "$ENV{DEFAULT_DOCKCROSS_IMAGE}") +set(CTEST_DASHBOARD_ROOT /work) +set(CTEST_SOURCE_DIRECTORY /work) + +set(CTEST_CONFIGURATION_TYPE Release) +set(CTEST_CMAKE_GENERATOR "Ninja") + +set(CTEST_BUILD_FLAGS "-j4") +set(CTEST_TEST_ARGS PARALLEL_LEVEL 8) + +# Build name +string(SUBSTRING $ENV{CIRCLE_SHA1} 0 7 commit) +set(what "#$ENV{CIRCLE_PR_NUMBER}") +if("$ENV{CIRCLE_PR_NUMBER}" STREQUAL "") + set(what "$ENV{CIRCLE_BRANCH}") +endif() +set(CTEST_BUILD_NAME "${PY_VERSION}-$ENV{CROSS_TRIPLE}_${what}_${commit}") + +set(dashboard_binary_name build) +set(dashboard_model Experimental) +set(dashboard_track Circle-CI) + +set(dashboard_cache "PYTHON_VERSION:STRING=${PY_VERSION} +") + +# Toolchain +if(EXISTS $ENV{CMAKE_TOOLCHAIN_FILE}) + set(dashboard_cache "${dashboard_cache} +CMAKE_TOOLCHAIN_FILE:FILEPATH=$ENV{CMAKE_TOOLCHAIN_FILE} +") +endif() + +# Include driver script +include(${CTEST_SCRIPT_DIRECTORY}/python_common.cmake) + +# Upload link to travis +#set(travis_url "/tmp/travis.url") +#file(WRITE ${travis_url} "https://travis-ci.org/$ENV{TRAVIS_REPO_SLUG}/builds/$ENV{TRAVIS_BUILD_ID}") +#ctest_upload(FILES ${travis_url}) +#ctest_submit(PARTS Upload) +#file(REMOVE ${travis_url}) diff --git a/.github/dashboard/circle_macos_dashboard.cmake b/.github/dashboard/circle_macos_dashboard.cmake new file mode 100644 index 000000000..7ca6d6ee8 --- /dev/null +++ b/.github/dashboard/circle_macos_dashboard.cmake @@ -0,0 +1,46 @@ +# Client maintainer: jchris.fillionr@kitware.com + +# Sanity checks +foreach(name IN ITEMS + PY_VERSION + ) + if("$ENV{${name}}" STREQUAL "") + message(FATAL_ERROR "Environment variable '${name}' is not set") + endif() +endforeach() + +# Extract major/minor/patch python versions +set(PY_VERSION $ENV{PY_VERSION}) +string(REGEX MATCH "([0-9])\\.([0-9]+)\\.([0-9]+)" _match ${PY_VERSION}) +if(_match STREQUAL "") + message(FATAL_ERROR "Environment variable 'PY_VERSION' is improperly set.") +endif() + +set(CTEST_SITE "circleci-macos") +set(CTEST_DASHBOARD_ROOT $ENV{CIRCLE_WORKING_DIRECTORY}/..) +set(CTEST_SOURCE_DIRECTORY $ENV{CIRCLE_WORKING_DIRECTORY}) + +set(CTEST_CMAKE_GENERATOR "Ninja") + +set(CTEST_BUILD_FLAGS "-j4") +set(CTEST_TEST_ARGS PARALLEL_LEVEL 8) + +# Build name +string(SUBSTRING $ENV{CIRCLE_SHA1} 0 7 commit) +set(what "#$ENV{CIRCLE_PR_NUMBER}") +if("$ENV{CIRCLE_PR_NUMBER}" STREQUAL "") + set(what "$ENV{CIRCLE_BRANCH}") +endif() +set(CTEST_BUILD_NAME "${PY_VERSION}_x64-${what}_${commit}") + +set(dashboard_binary_name build) +set(dashboard_model Experimental) +set(dashboard_track Circle-CI-macOS) + +set(dashboard_cache "BUILD_LIBPYTHON_SHARED:BOOL=ON +PYTHON_VERSION:STRING=${PY_VERSION} +") + +# Include driver script +include(${CTEST_SCRIPT_DIRECTORY}/python_common.cmake) + diff --git a/.github/dashboard/github_actions_dashboard.cmake b/.github/dashboard/github_actions_dashboard.cmake new file mode 100644 index 000000000..2e8a0aa33 --- /dev/null +++ b/.github/dashboard/github_actions_dashboard.cmake @@ -0,0 +1,63 @@ +# Client maintainer: jchris.fillionr@kitware.com + +# Sanity checks +foreach(name IN ITEMS + PY_VERSION + RUNNER_OS + RUNNER_ARCH + CC + CXX + ) + if("$ENV{${name}}" STREQUAL "") + message(FATAL_ERROR "Environment variable '${name}' is not set") + endif() +endforeach() + +# Extract major/minor/patch python versions +set(PY_VERSION $ENV{PY_VERSION}) +string(REGEX MATCH "([0-9])\\.([0-9]+)\\.([0-9]+)" _match ${PY_VERSION}) +if(_match STREQUAL "") + message(FATAL_ERROR "Environment variable 'PY_VERSION' is improperly set.") +endif() + +set(CTEST_SITE "$ENV{RUNNER_OS}-$ENV{RUNNER_ARCH}") +set(CTEST_DASHBOARD_ROOT $ENV{GITHUB_WORKSPACE}) +set(CTEST_SOURCE_DIRECTORY $ENV{GITHUB_WORKSPACE}/src) + +set(CTEST_CMAKE_GENERATOR "Unix Makefiles") + +set(CTEST_BUILD_FLAGS "-j4") +set(CTEST_TEST_ARGS PARALLEL_LEVEL 8) + +# Build name +string(SUBSTRING $ENV{GITHUB_SHA} 0 7 commit) +set(what "#$ENV{GITHUB_HEAD_REF}") +if("$ENV{GITHUB_HEAD_REF}" STREQUAL "") + set(what "$ENV{GITHUB_REF_NAME}") +endif() +set(CTEST_BUILD_NAME "${PY_VERSION}_x64-${what}_${commit}") + +set(dashboard_binary_name build) +set(dashboard_model Experimental) +set(dashboard_track GitHub-Actions) + +# Reading initial dashboard cache +set(_dashboard_cache_path "${CTEST_SCRIPT_DIRECTORY}/initial-dashboard-cache.txt") +set(_msg "Looking for ${_dashboard_cache_path}") +message(STATUS "${_msg}") +if(EXISTS "${_dashboard_cache_path}") + message(STATUS "${_msg} - found") + file(READ "${_dashboard_cache_path}" dashboard_cache) +else() + message(STATUS "${_msg} - not found") + set(dashboard_cache "") +endif() + +set(dashboard_cache "${dashboard_cache} +BUILD_LIBPYTHON_SHARED:BOOL=ON +PYTHON_VERSION:STRING=${PY_VERSION} +") + +# Include driver script +include(${CTEST_SCRIPT_DIRECTORY}/python_common.cmake) + diff --git a/.github/dashboard/github_actions_win_dashboard.cmake b/.github/dashboard/github_actions_win_dashboard.cmake new file mode 100644 index 000000000..f76e95b37 --- /dev/null +++ b/.github/dashboard/github_actions_win_dashboard.cmake @@ -0,0 +1,52 @@ +# Client maintainer: jchris.fillionr@kitware.com + +# Sanity checks +foreach(name IN ITEMS + CONFIGURATION + GENERATOR + PLATFORM + PY_VERSION + ) + if("$ENV{${name}}" STREQUAL "") + message(FATAL_ERROR "Environment variable '${name}' is not set") + endif() +endforeach() + +# Extract major/minor/patch python versions +set(PY_VERSION $ENV{PY_VERSION}) +string(REGEX MATCH "([0-9])\\.([0-9]+)\\.([0-9]+)" _match ${PY_VERSION}) +if(_match STREQUAL "") + message(FATAL_ERROR "Environment variable 'PY_VERSION' is improperly set.") +endif() + +set(CTEST_SITE "github-actions-window") +set(CTEST_DASHBOARD_ROOT $ENV{GITHUB_WORKSPACE}) +set(CTEST_SOURCE_DIRECTORY $ENV{GITHUB_WORKSPACE}/src) + +set(CTEST_CONFIGURATION_TYPE $ENV{CONFIGURATION}) +set(CTEST_CMAKE_GENERATOR "$ENV{GENERATOR}") +set(CTEST_CMAKE_GENERATOR_PLATFORM $ENV{PLATFORM}) + +set(CTEST_BUILD_FLAGS "/m") +set(CTEST_TEST_ARGS PARALLEL_LEVEL 8) + +# Build name +# Build name +string(SUBSTRING $ENV{GITHUB_SHA} 0 7 commit) +set(what "#$ENV{GITHUB_HEAD_REF}") +if("$ENV{GITHUB_HEAD_REF}" STREQUAL "") + set(what "$ENV{GITHUB_REF_NAME}") +endif() +set(CTEST_BUILD_NAME "${PY_VERSION}-${CTEST_CMAKE_GENERATOR_PLATFORM}-${CTEST_CONFIGURATION_TYPE}_${what}_${commit}") + +set(dashboard_binary_name build) +set(dashboard_model Experimental) +set(dashboard_track GitHub-Actions) + +set(dashboard_cache "BUILD_LIBPYTHON_SHARED:BOOL=ON +PYTHON_VERSION:STRING=${PY_VERSION} +") + +# Include driver script +include(${CTEST_SCRIPT_DIRECTORY}/python_common.cmake) + diff --git a/.github/dashboard/python_common.cmake b/.github/dashboard/python_common.cmake new file mode 100644 index 000000000..27203df25 --- /dev/null +++ b/.github/dashboard/python_common.cmake @@ -0,0 +1,484 @@ +# Python Common Dashboard Script +# +# This script contains basic dashboard driver code common to all +# clients. +# +# Put this script in a directory such as "~/Dashboards/Scripts" or +# "c:/Dashboards/Scripts". Create a file next to this script, say +# 'my_dashboard.cmake', with code of the following form: +# +# # Client maintainer: me@mydomain.net +# set(CTEST_SITE "machine.site") +# set(CTEST_BUILD_NAME "Platform-Compiler") +# set(CTEST_CONFIGURATION_TYPE Debug) +# set(CTEST_CMAKE_GENERATOR "Unix Makefiles") +# include(${CTEST_SCRIPT_DIRECTORY}/python_common.cmake) +# +# Then run a scheduled task (cron job) with a command line such as +# +# ctest -S ~/Dashboards/Scripts/my_dashboard.cmake -V +# +# By default the source and build trees will be placed in the path +# "../MyTests/" relative to your script location. +# +# The following variables may be set before including this script +# to configure it: +# +# dashboard_model = Nightly | Experimental | Continuous +# dashboard_track = Optional track to submit dashboard to +# dashboard_disable_loop = For continuous dashboards, disable loop. +# dashboard_root_name = Change name of "MyTests" directory. This is +# ignored if CTEST_DASHBOARD_ROOT is set. +# dashboard_source_name = Name of source directory (default: python-cmake-buildsystem) +# dashboard_binary_name = Name of binary directory (default: python-cmake-buildsystem-build) +# dashboard_cache = Initial CMakeCache.txt file content +# dashboard_no_test = True to disable tests +# dashboard_do_coverage = True to enable coverage (ex: gcov) +# dashboard_do_memcheck = True to enable memcheck (ex: valgrind) +# CTEST_CHECKOUT_COMMAND = Custom source tree checkout comamnd (primarilly +# for if the VCS is not git). +# CTEST_BUILD_FLAGS = build tool arguments (ex: -j2) +# CTEST_DASHBOARD_ROOT = Where to put source and build trees +# CTEST_TEST_CTEST = Whether to run long CTestTest* tests +# CTEST_TEST_TIMEOUT = Per-test timeout length +# CTEST_TEST_ARGS = ctest_test args (ex: PARALLEL_LEVEL 4) +# CMAKE_MAKE_PROGRAM = Path to "make" tool to use +# +# Options to configure Git: +# CTEST_GIT_COMMAND = Path to the git command-line client. +# dashboard_git_url = Custom git clone url +# dashboard_git_branch = Custom remote branch to track +# dashboard_git_crlf = Value of core.autocrlf for repository +# +# The following macros will be invoked before the corresponding step if they +# are defined: +# +# dashboard_hook_init = End of initialization, before loop +# dashboard_hook_start = Start of loop body, before ctest_start +# dashboard_hook_started = Start of loop body, after ctest_start +# dashboard_hook_build = Before ctest_build +# dashboard_hook_test = Before ctest_test +# dashboard_hook_end = End of body loop, after ctest_submit. +# +# For Makefile generators the script may be executed from an +# environment already configured to use the desired compilers. +# Alternatively the environment may be set at the top of the script: +# +# set(ENV{CC} /path/to/cc) # C compiler +# set(ENV{CXX} /path/to/cxx) # C++ compiler +# set(ENV{FC} /path/to/fc) # Fortran compiler (optional) +# set(ENV{LD_LIBRARY_PATH} /path/to/vendor/lib) # (if necessary) + +#============================================================================= +# Copyright 2010-2015 Kitware, Inc. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# +# * Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# * Neither the name of Kitware, Inc. nor the names of its contributors +# may be used to endorse or promote products derived from this +# software without specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +# HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +#============================================================================= + +cmake_minimum_required(VERSION 3.13.5) + +set(CTEST_PROJECT_NAME CPython) +set(dashboard_user_home "$ENV{HOME}") + +# Select the top dashboard directory. +if(NOT DEFINED dashboard_root_name) + set(dashboard_root_name "MyTests") +endif() +if(NOT DEFINED CTEST_DASHBOARD_ROOT) + get_filename_component(CTEST_DASHBOARD_ROOT "${CTEST_SCRIPT_DIRECTORY}/../${dashboard_root_name}" ABSOLUTE) +endif() + +# Select the model (Nightly, Experimental, Continuous). +if(NOT DEFINED dashboard_model) + set(dashboard_model Nightly) +endif() +if(NOT "${dashboard_model}" MATCHES "^(Nightly|Experimental|Continuous)$") + message(FATAL_ERROR "dashboard_model must be Nightly, Experimental, or Continuous") +endif() + +# Default to a Debug build. +if(NOT DEFINED CTEST_CONFIGURATION_TYPE AND DEFINED CTEST_BUILD_CONFIGURATION) + set(CTEST_CONFIGURATION_TYPE ${CTEST_BUILD_CONFIGURATION}) +endif() + +if(NOT DEFINED CTEST_CONFIGURATION_TYPE) + set(CTEST_CONFIGURATION_TYPE Debug) +endif() + +# Choose CTest reporting mode. +if(dashboard_bootstrap) + # Launchers do not work during bootstrap: no ctest available. + set(CTEST_USE_LAUNCHERS 0) +elseif(NOT "${CTEST_CMAKE_GENERATOR}" MATCHES "Make|Ninja") + # Launchers work only with Makefile and Ninja generators. + set(CTEST_USE_LAUNCHERS 0) +elseif(NOT DEFINED CTEST_USE_LAUNCHERS) + # The setting is ignored by CTest < 2.8 so we need no version test. + set(CTEST_USE_LAUNCHERS 1) +endif() + +# Configure testing. +if(NOT DEFINED CTEST_TEST_CTEST) + set(CTEST_TEST_CTEST 1) +endif() +if(NOT CTEST_TEST_TIMEOUT) + set(CTEST_TEST_TIMEOUT 1500) +endif() + +# Select Git source to use. +if(NOT DEFINED dashboard_git_url) + set(dashboard_git_url "git://github.com/jcfr/python-cmake-buildsystem.git") +endif() +if(NOT DEFINED dashboard_git_branch) + set(dashboard_git_branch master) + #if("${dashboard_model}" STREQUAL "Nightly") + # set(dashboard_git_branch nightly) + #else() + # set(dashboard_git_branch next) + #endif() +endif() +if(NOT DEFINED dashboard_git_crlf) + if(UNIX) + set(dashboard_git_crlf false) + else(UNIX) + set(dashboard_git_crlf true) + endif(UNIX) +endif() + +# Look for a GIT command-line client. +if(NOT DEFINED CTEST_GIT_COMMAND) + find_program(CTEST_GIT_COMMAND + NAMES git git.cmd + PATH_SUFFIXES Git/cmd Git/bin + ) +endif() +if(NOT CTEST_GIT_COMMAND) + message(FATAL_ERROR "CTEST_GIT_COMMAND not available!") +endif() + +# Select a source directory name. +if(NOT DEFINED CTEST_SOURCE_DIRECTORY) + if(DEFINED dashboard_source_name) + set(CTEST_SOURCE_DIRECTORY ${CTEST_DASHBOARD_ROOT}/${dashboard_source_name}) + else() + set(CTEST_SOURCE_DIRECTORY ${CTEST_DASHBOARD_ROOT}/python-cmake-buildsystem) + endif() +endif() + +# Select a build directory name. +if(NOT DEFINED CTEST_BINARY_DIRECTORY) + if(DEFINED dashboard_binary_name) + set(CTEST_BINARY_DIRECTORY ${CTEST_DASHBOARD_ROOT}/${dashboard_binary_name}) + else() + set(CTEST_BINARY_DIRECTORY ${CTEST_SOURCE_DIRECTORY}-build) + endif() +endif() + +# Delete source tree if it is incompatible with current VCS. +if(EXISTS ${CTEST_SOURCE_DIRECTORY}) + if(NOT EXISTS "${CTEST_SOURCE_DIRECTORY}/.git") + set(vcs_refresh "because it is not managed by git.") + else() + execute_process( + COMMAND ${CTEST_GIT_COMMAND} reset --hard + WORKING_DIRECTORY "${CTEST_SOURCE_DIRECTORY}" + OUTPUT_VARIABLE output + ERROR_VARIABLE output + RESULT_VARIABLE failed + ) + if(failed) + set(vcs_refresh "because its .git may be corrupted.") + endif() + endif() + if(vcs_refresh AND "${CTEST_SOURCE_DIRECTORY}" MATCHES "/CMake[^/]*") + message("Deleting source tree\n ${CTEST_SOURCE_DIRECTORY}\n${vcs_refresh}") + file(REMOVE_RECURSE "${CTEST_SOURCE_DIRECTORY}") + endif() +endif() + +# Support initial checkout if necessary. +if(NOT EXISTS "${CTEST_SOURCE_DIRECTORY}" + AND NOT DEFINED CTEST_CHECKOUT_COMMAND) + get_filename_component(_name "${CTEST_SOURCE_DIRECTORY}" NAME) + + # Generate an initial checkout script. + set(ctest_checkout_script ${CTEST_DASHBOARD_ROOT}/${_name}-init.cmake) + file(WRITE ${ctest_checkout_script} "# git repo init script for ${_name} +execute_process( + COMMAND \"${CTEST_GIT_COMMAND}\" clone -n -b ${dashboard_git_branch} -- \"${dashboard_git_url}\" + \"${CTEST_SOURCE_DIRECTORY}\" + ) +if(EXISTS \"${CTEST_SOURCE_DIRECTORY}/.git\") + execute_process( + COMMAND \"${CTEST_GIT_COMMAND}\" config core.autocrlf ${dashboard_git_crlf} + WORKING_DIRECTORY \"${CTEST_SOURCE_DIRECTORY}\" + ) + execute_process( + COMMAND \"${CTEST_GIT_COMMAND}\" checkout + WORKING_DIRECTORY \"${CTEST_SOURCE_DIRECTORY}\" + ) +endif() +") + set(CTEST_CHECKOUT_COMMAND "\"${CMAKE_COMMAND}\" -P \"${ctest_checkout_script}\"") +endif() + +#----------------------------------------------------------------------------- + +# Send the main script as a note. +list(APPEND CTEST_NOTES_FILES + "${CTEST_SCRIPT_DIRECTORY}/${CTEST_SCRIPT_NAME}" + "${CMAKE_CURRENT_LIST_FILE}" + ) + +# Check for required variables. +foreach(req + CTEST_CMAKE_GENERATOR + CTEST_SITE + CTEST_BUILD_NAME + ) + if(NOT DEFINED ${req}) + message(FATAL_ERROR "The containing script must set ${req}") + endif() +endforeach(req) + +# Workaround for a CDash issue where colons (:) in CTEST_SITE cause Update and +# Configure/Build/Test submissions to appear as separate rows. Replace colons +# with underscores to ensure all parts are grouped under a single entry. +# See: https://github.com/Kitware/CDash/issues/2905 +string(REPLACE ":" "_" CTEST_SITE "${CTEST_SITE}") + +# Print summary information. +set(vars "") +foreach(v + CTEST_SITE + CTEST_BUILD_NAME + CTEST_SOURCE_DIRECTORY + CTEST_BINARY_DIRECTORY + CTEST_CMAKE_GENERATOR + CTEST_CMAKE_GENERATOR_PLATFORM + CTEST_CONFIGURATION_TYPE + CTEST_GIT_COMMAND + CTEST_CHECKOUT_COMMAND + CTEST_CONFIGURE_COMMAND + CTEST_SCRIPT_DIRECTORY + CTEST_USE_LAUNCHERS + ) + if (DEFINED ${v}) + set(vars "${vars} ${v}=[${${v}}]\n") + endif() +endforeach(v) +message("Dashboard script configuration:\n${vars}\n") + +# Avoid non-ascii characters in tool output. +set(ENV{LC_ALL} C) + +# Helper macro to write the initial cache. +macro(write_cache) + set(cache_build_type "") + set(cache_make_program "") + if(CTEST_CMAKE_GENERATOR MATCHES "Make|Ninja") + set(cache_build_type CMAKE_BUILD_TYPE:STRING=${CTEST_CONFIGURATION_TYPE}) + if(CMAKE_MAKE_PROGRAM) + set(cache_make_program CMAKE_MAKE_PROGRAM:FILEPATH=${CMAKE_MAKE_PROGRAM}) + endif() + endif() + file(WRITE ${CTEST_BINARY_DIRECTORY}/CMakeCache.txt " +SITE:STRING=${CTEST_SITE} +BUILDNAME:STRING=${CTEST_BUILD_NAME} +CTEST_USE_LAUNCHERS:BOOL=${CTEST_USE_LAUNCHERS} +DART_TESTING_TIMEOUT:STRING=${CTEST_TEST_TIMEOUT} +GIT_EXECUTABLE:FILEPATH=${CTEST_GIT_COMMAND} +${cache_build_type} +${cache_make_program} +${dashboard_cache} +") +endmacro(write_cache) + +# Start with a fresh build tree. +if(EXISTS "${CTEST_BINARY_DIRECTORY}" AND + NOT "${CTEST_SOURCE_DIRECTORY}" STREQUAL "${CTEST_BINARY_DIRECTORY}") + message("Clearing build tree...") + ctest_empty_binary_directory(${CTEST_BINARY_DIRECTORY}) +endif() +file(MAKE_DIRECTORY "${CTEST_BINARY_DIRECTORY}") + +set(dashboard_continuous 0) +if("${dashboard_model}" STREQUAL "Continuous") + set(dashboard_continuous 1) +endif() + +if("${dashboard_model}" STREQUAL "Experimental") + set(CTEST_UPDATE_VERSION_ONLY 1) # Introduced in CMake >= 3.1.0 +endif() + +# CTest 2.6 crashes with message() after ctest_test. +macro(safe_message) + if(NOT "${CMAKE_VERSION}" VERSION_LESS 2.8 OR NOT safe_message_skip) + message(${ARGN}) + endif() +endmacro() + +if(COMMAND dashboard_hook_init) + dashboard_hook_init() +endif() + +set(dashboard_done 0) +while(NOT dashboard_done) + if(dashboard_continuous) + set(START_TIME ${CTEST_ELAPSED_TIME}) + endif() + + # Start a new submission. + if(COMMAND dashboard_hook_start) + dashboard_hook_start() + endif() + if(dashboard_track) + ctest_start(${dashboard_model} TRACK ${dashboard_track}) + else() + ctest_start(${dashboard_model}) + endif() + if(COMMAND dashboard_hook_started) + dashboard_hook_started() + endif() + + # Look for updates. + ctest_update(RETURN_VALUE count) + set(CTEST_CHECKOUT_COMMAND) # checkout on first iteration only + safe_message("Found ${count} changed files") + + ctest_submit(PARTS Update) + + # Always build if the tree is fresh. + set(dashboard_fresh 0) + if(NOT EXISTS "${CTEST_BINARY_DIRECTORY}/CMakeCache.txt") + set(dashboard_fresh 1) + safe_message("Starting fresh build...") + write_cache() + endif() + + # Additional CMake configure options can be specified in a commit message + # using one or multiple line of the form "[cmake ;;...]". + # + # If multiple matching lines are found, the project will be configured passing + # all without doing any particular filtering. + + # 1) Extract additional CMake configure option from last commit message + # that is not associated with a merge commit. + execute_process( + COMMAND ${CTEST_GIT_COMMAND} log -1 --pretty=%B --max-parents=1 + WORKING_DIRECTORY "${CTEST_SOURCE_DIRECTORY}" + OUTPUT_VARIABLE output + ERROR_VARIABLE output + RESULT_VARIABLE failed + ) + if(failed) + message(FATAL_ERROR "Failed to extract last commit message from git history !") + endif() + + # 2) Split by newlines + # Copied from http://www.cmake.org/pipermail/cmake/2007-May/014222.html + string(REGEX REPLACE ";" "\\\\;" output "${output}") + string(REGEX REPLACE "\n" ";" output "${output}") + + # 3) Loop over all lines, match "[cmake ...] and extract + set(CMAKE_CONFIGURE_ARGS_FROM_COMMITMSG ) + foreach(line ${output}) + string(REGEX MATCH "^\\[cmake (.+)\\]" raw_cmake_comment ${line}) + if(raw_cmake_comment) + list(APPEND CMAKE_CONFIGURE_ARGS_FROM_COMMITMSG ${CMAKE_MATCH_1}) + endif() + endforeach() + + set(ctest_configure_options) + if(CMAKE_CONFIGURE_ARGS_FROM_COMMITMSG) + set(ctest_configure_options ${CMAKE_CONFIGURE_ARGS_FROM_COMMITMSG}) + message("CMake configure options from commit msg: ${CMAKE_CONFIGURE_ARGS_FROM_COMMITMSG}") + else() + message("CMake configure options from commit msg: Didn't find any [cmake ] directives in commit message.") + endif() + + if(dashboard_fresh OR NOT dashboard_continuous OR count GREATER 0) + + if(ctest_configure_options) + ctest_configure(OPTIONS "${ctest_configure_options}") + else() + ctest_configure() + endif() + + ctest_submit(PARTS Configure) + ctest_read_custom_files(${CTEST_BINARY_DIRECTORY}) + + # Submit files associated with the CTEST_NOTES_FILES variables + ctest_submit(PARTS Notes) + + if(COMMAND dashboard_hook_build) + dashboard_hook_build() + endif() + ctest_build() + ctest_submit(PARTS Build) + + if(COMMAND dashboard_hook_test) + dashboard_hook_test() + endif() + if(NOT dashboard_no_test) + ctest_test(${CTEST_TEST_ARGS}) + ctest_submit(PARTS Test) + endif() + set(safe_message_skip 1) # Block further messages + + if(dashboard_do_coverage) + ctest_coverage() + ctest_submit(PARTS Coverage) + endif() + + if(dashboard_do_memcheck) + ctest_memcheck(${CTEST_TEST_ARGS}) + ctest_submit(PARTS MemCheck) + endif() + + if(COMMAND dashboard_hook_end) + dashboard_hook_end() + endif() + + endif() + + if(dashboard_continuous AND NOT dashboard_disable_loop) + # Delay until at least 5 minutes past START_TIME + ctest_sleep(${START_TIME} 300 ${CTEST_ELAPSED_TIME}) + if(${CTEST_ELAPSED_TIME} GREATER 57600) + set(dashboard_done 1) + endif() + else() + # Not continuous, so we are done. + set(dashboard_done 1) + endif() + + set(ENV{HOME} "${dashboard_user_home}") +endwhile() + diff --git a/.github/workflows/CI.yml b/.github/workflows/CI.yml index 552b404f7..298cb4e98 100644 --- a/.github/workflows/CI.yml +++ b/.github/workflows/CI.yml @@ -37,33 +37,159 @@ jobs: with: version: 1.10.0 - - name: Download dashboard script - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 - with: - repository: 'python-cmake-buildsystem/python-cmake-buildsystem' - ref: dashboard - fetch-depth: 0 - path: scripts - - name: Writing initial dashboard cache shell: bash run: | - cat > scripts/initial-dashboard-cache.txt << EOF + cat > src/.github/dashboard/initial-dashboard-cache.txt << EOF ${{ matrix.initial-dashboard-cache }} EOF - cat scripts/initial-dashboard-cache.txt + cat src/.github/dashboard/initial-dashboard-cache.txt - name: Build & Test - run: ctest --timeout 360 -S scripts/github_actions_dashboard.cmake -VV + run: ctest --timeout 360 -S src/.github/dashboard/github_actions_dashboard.cmake -VV env: PY_VERSION: ${{ matrix.python-version }} CC: ${{ matrix.c-compiler }} CXX: ${{ matrix.cxx-compiler }} + tests-android: + runs-on: ${{ matrix.host }} + strategy: + matrix: + ndk-arch: [x86_64, arm64-v8a, x86, armeabi-v7a] + host: [ubuntu-24.04] + python-version: [3.8.20, 3.9.22, 3.10.17, 3.11.12] + name: python-android-${{ matrix.ndk-arch }}-${{ matrix.python-version }}-${{ matrix.host }} + steps: + - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 + with: + fetch-depth: 0 + path: src + - name: Enable KVM + run: | + echo 'KERNEL=="kvm", GROUP="kvm", MODE="0666", OPTIONS+="static_node=kvm"' | sudo tee /etc/udev/rules.d/99-kvm4all.rules + sudo udevadm control --reload-rules + sudo udevadm trigger --name-match=kvm + - name: Make build and prefix directories + run: | + mkdir build + mkdir install-prefix + mkdir bootstrap-build + mkdir bootstrap-install-prefix + - name: Check for bootstrap needed + id: check-bootstrap + shell: cmake -P {0} + run: | + string(REPLACE "." ";" VERSION_LIST "${{ matrix.python-version }}") + list(GET VERSION_LIST 0 PY_VERSION_MAJOR) + list(GET VERSION_LIST 1 PY_VERSION_MINOR) + list(GET VERSION_LIST 2 PY_VERSION_PATCH) + set(PY_VERSION "${PY_VERSION_MAJOR}.${PY_VERSION_MINOR}.${PY_VERSION_PATCH}") + if(PY_VERSION VERSION_GREATER_EQUAL "3.11") + file(APPEND "$ENV{GITHUB_OUTPUT}" "needed=yes") + endif() + - name: Bootstrap + if: steps.check-bootstrap.outputs.needed == 'yes' + run: | + cd bootstrap-build + cmake -DCMAKE_INSTALL_PREFIX:PATH=../bootstrap-install-prefix -DPYTHON_VERSION=${{ matrix.python-version }} $(pwd)/../src/ + cmake --build . -- VERBOSE=1 + cmake --build . --target install + - name: run action + uses: reactivecircus/android-emulator-runner@v2 + with: + api-level: ${{ startsWith(matrix.ndk-arch, 'x86') && 21 || 30 }} + target: ${{ startsWith(matrix.ndk-arch, 'x86') && 'default' || 'google_apis' }} + arch: ${{ matrix.ndk-arch == 'x86' && 'x86' || 'x86_64' }} + profile: Galaxy Nexus + cores: 2 + ram-size: 2048M + sdcard-path-or-size: 100M + emulator-build: 7425822 # https://github.com/ReactiveCircus/android-emulator-runner/issues/160 + avd-name: test + force-avd-creation: false + emulator-options: -no-snapshot-save -no-window -gpu swiftshader_indirect -noaudio -no-boot-anim -camera-back none + disable-animations: true + working-directory: build/ + ndk: 23.0.7421159 + channel: beta + script: | + adb devices + cmake -DANDROID_NDK=/usr/local/lib/android/sdk/ndk/23.0.7421159/ -DCMAKE_INSTALL_PREFIX:PATH=../install-prefix -DCMAKE_TOOLCHAIN_FILE=/usr/local/lib/android/sdk/ndk/23.0.7421159/build/cmake/android.toolchain.cmake -DANDROID_ABI=${{ matrix.ndk-arch }} -DCMAKE_CROSSCOMPILING_EMULATOR=$(pwd)/../src/.github/workflows/adb-emu.sh -DANDROID_ALLOW_UNDEFINED_SYMBOLS=On -DENABLE_DECIMAL=Off -DENABLE_CTYPES=Off -DENABLE_CODECS_JP=OFF -DENABLE_CODECS_KR=OFF -DENABLE_CODECS_TW=OFF -DENABLE_MULTIBYTECODEC=OFF -DENABLE_CODECS_CN=OFF -DENABLE_CODECS_HK=OFF -DENABLE_CODECS_ISO2022=OFF -DBUILD_EXTENSIONS_AS_BUILTIN=On -DANDROID_PLATFORM=android-21 -DPYTHON_VERSION=${{ matrix.python-version }} -DBUILD_PYTHON=../bootstrap-install-prefix/bin/python $(pwd)/../src/ + cmake --build . -- VERBOSE=1 + cmake --build . --target install + + tests-linux: + name: python-linux-${{ matrix.python-arch }}-${{ matrix.python-version }} + runs-on: ubuntu-latest + strategy: + fail-fast: false + matrix: + python-arch: [x64, x86] + python-version: [3.6.15, 3.7.17, 3.8.20, 3.9.22, 3.10.17, 3.11.12, 3.12.10] + container: + image: dockcross/linux-${{ matrix.python-arch }} + steps: + - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 + with: + fetch-depth: 0 + path: src + - run: | + sudo apt-get update + sudo apt-get install -y \ + libbz2-dev \ + libdb-dev \ + libffi-dev \ + libgdbm-compat-dev \ + libgdbm-dev \ + liblzma-dev \ + libncursesw5-dev \ + libreadline-dev \ + libsqlite3-dev \ + libssl-dev \ + tcl-dev \ + tk-dev + - name: Writing initial dashboard cache + shell: bash + run: | + cat > src/.github/dashboard/initial-dashboard-cache.txt << EOF + ${{ matrix.initial-dashboard-cache }} + EOF + cat src/.github/dashboard/initial-dashboard-cache.txt + - name: Build & Test + run: ctest --timeout 360 -S src/.github/dashboard/github_actions_dashboard.cmake -VV + env: + PY_VERSION: ${{ matrix.python-version }} + + tests-windows: + name: python-${{ matrix.python-version }}-win-${{ matrix.python-arch }} + runs-on: windows-2022 + strategy: + fail-fast: false + matrix: + python-arch: [x64] + python-version: [3.6.15, 3.7.17, 3.8.20, 3.9.22, 3.10.17, 3.11.12, 3.12.10] + generator: ["Visual Studio 17 2022"] + steps: + - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 + with: + fetch-depth: 0 + path: src + - name: Build & Test + run: ctest -C $Env:CONFIGURATION -S src/.github/dashboard/github_actions_win_dashboard.cmake -VV + env: + PY_VERSION: ${{ matrix.python-version }} + CONFIGURATION: Release + GENERATOR: ${{ matrix.generator }} + PLATFORM: ${{ matrix.python-arch }} + pass: # This job does nothing and is only used for the branch protection if: always() needs: - tests + - tests-android + - tests-linux + - tests-windows runs-on: ubuntu-latest diff --git a/.github/workflows/adb-emu.sh b/.github/workflows/adb-emu.sh new file mode 100755 index 000000000..f7336503d --- /dev/null +++ b/.github/workflows/adb-emu.sh @@ -0,0 +1,17 @@ +#!/bin/sh +adb push "$1" /data/local/tmp/ 1>/dev/null 2>/dev/null +BINARY=$(basename "$1") +if [ $# -eq 1 ]; then + adb shell "/data/local/tmp/${BINARY}" +elif [ $# -eq 3 ]; then + adb push "$2" /data/local/tmp/ 1>/dev/null 2>/dev/null + adb shell "/data/local/tmp/${BINARY}" "/data/local/tmp/$(basename $2)" "/data/local/tmp/$(basename $3)" + adb pull "/data/local/tmp/$(basename $3)" "$3" 1>/dev/null 2>/dev/null +elif [ $# -eq 4 ] && [ "${BINARY}" = "_freeze_importlib" ]; then + adb push "$3" /data/local/tmp/ 1>/dev/null 2>/dev/null + adb shell "/data/local/tmp/${BINARY}" "$2" "/data/local/tmp/$(basename $3)" "/data/local/tmp/$(basename $4)" + adb pull "/data/local/tmp/$(basename $4)" "$4" 1>/dev/null 2>/dev/null +else + echo "Unknown number of arguments $# for ${BINARY}" + exit 1 +fi diff --git a/CMakeLists.txt b/CMakeLists.txt index 730e0fa21..7cabf83cf 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -163,6 +163,28 @@ else() set(WITH_STATIC_DEPENDENCIES 0) endif() +if(ANDROID AND PY_VERSION VERSION_GREATER_EQUAL "3.11") + set(BUILD_PYTHON "" CACHE PATH "path to build ``python`` binary for cross compiling") + if(NOT BUILD_PYTHON) + message(FATAL_ERROR "Cross compiling requires -DBUILD_PYTHON=") + endif() + if(NOT EXISTS ${BUILD_PYTHON}) + message(FATAL_ERROR "invalid or missing build python binary ${BUILD_PYTHON}") + endif() + execute_process( + COMMAND ${BUILD_PYTHON} -c "import sys; print(f'{sys.version_info.major}.{sys.version_info.minor}')" + OUTPUT_VARIABLE BUILD_PYTHON_VER + OUTPUT_STRIP_TRAILING_WHITESPACE + RESULT_VARIABLE BUILD_PYTHON_EXEC_RESULT + ) + if(NOT BUILD_PYTHON_EXEC_RESULT EQUAL 0) + message(FATAL_ERROR "can not execute build python binary ${BUILD_PYTHON}") + endif() + if(NOT "${BUILD_PYTHON_VER}" STREQUAL "${PY_VERSION_MAJOR}.${PY_VERSION_MINOR}") + message(FATAL_ERROR "\"${BUILD_PYTHON}\" has incompatible version ${BUILD_PYTHON_VER} (expected: ${PY_VERSION_MAJOR}.${PY_VERSION_MINOR})") + endif() +endif() + # Detect source directory set(_landmark "pyconfig.h.in") # CMake will look for this file. if(NOT (SRC_DIR AND EXISTS ${SRC_DIR}/${_landmark})) @@ -799,7 +821,7 @@ if(UNIX) # Makefile set(MAKEFILE_LDSHARED_FLAGS "-shared") - if(APPLE) + if(APPLE OR ANDROID) set(MAKEFILE_LDSHARED_FLAGS "-dynamiclib -headerpad_max_install_names -undefined dynamic_lookup") endif() configure_file(cmake/makefile-variables.in diff --git a/cmake/ConfigureChecks.cmake b/cmake/ConfigureChecks.cmake index 5ed2c5b7a..ecde8b91d 100644 --- a/cmake/ConfigureChecks.cmake +++ b/cmake/ConfigureChecks.cmake @@ -356,7 +356,11 @@ check_include_files(grp.h HAVE_GRP_H) check_include_files(ieeefp.h HAVE_IEEEFP_H) check_include_files(inttypes.h HAVE_INTTYPES_H) # libffi and cpython check_include_files(io.h HAVE_IO_H) -check_include_files(langinfo.h HAVE_LANGINFO_H) +if (ANDROID) + set(HAVE_LANGINFO_H 0) # Android cann't link functions from langinfo.h +else() + check_include_files(langinfo.h HAVE_LANGINFO_H) +endif() check_include_files(libintl.h HAVE_LIBINTL_H) check_include_files(libutil.h HAVE_LIBUTIL_H) check_include_files(linux/tipc.h HAVE_LINUX_TIPC_H) @@ -532,7 +536,7 @@ find_library(HAVE_LIBTERMCAP termcap) set(LIBUTIL_LIBRARIES ) set(LIBUTIL_EXPECTED 1) -if(CMAKE_SYSTEM MATCHES "VxWorks\\-7$") +if(ANDROID OR CMAKE_SYSTEM MATCHES "VxWorks\\-7$") set(LIBUTIL_EXPECTED 0) set(HAVE_LIBUTIL 0) endif() @@ -1298,60 +1302,38 @@ python_platform_test( # Check for various properties of floating point # ####################################################################### - -# Check whether C doubles are little-endian IEEE 754 binary64 -set(check_src ${PROJECT_BINARY_DIR}/CMakeFiles/ac_cv_little_endian_double.c) -file(WRITE ${check_src} "#include -int main() { - double x = 9006104071832581.0; - if (memcmp(&x, \"\\x05\\x04\\x03\\x02\\x01\\xff\\x3f\\x43\", 8) == 0) - return 0; - else - return 1; -} -") -python_platform_test_run( - DOUBLE_IS_LITTLE_ENDIAN_IEEE754 - "Checking whether C doubles are little-endian IEEE 754 binary64" - ${check_src} - DIRECT - ) - -# Check whether C doubles are big-endian IEEE 754 binary64 set(check_src ${PROJECT_BINARY_DIR}/CMakeFiles/ac_cv_big_endian_double.c) -file(WRITE ${check_src} "#include -int main() { - double x = 9006104071832581.0; - if (memcmp(&x, \"\\x43\\x3f\\xff\\x01\\x02\\x03\\x04\\x05\", 8) == 0) - return 0; - else - return 1; -} +file(WRITE ${check_src} " +double d = 90904234967036810337470478905505011476211692735615632014797120844053488865816695273723469097858056257517020191247487429516932130503560650002327564517570778480236724525140520121371739201496540132640109977779420565776568942592.0; ") -python_platform_test_run( - DOUBLE_IS_BIG_ENDIAN_IEEE754 - "Checking whether C doubles are big-endian IEEE 754 binary64" - ${check_src} - DIRECT - ) -# Check whether C doubles are ARM mixed-endian IEEE 754 binary64 -set(check_src ${PROJECT_BINARY_DIR}/CMakeFiles/ac_cv_mixed_endian_double.c) -file(WRITE ${check_src} "#include -int main() { - double x = 9006104071832581.0; - if (memcmp(&x, \"\\x01\\xff\\x3f\\x43\\x05\\x04\\x03\\x02\", 8) == 0) - return 0; - else - return 1; -} -") -python_platform_test_run( - DOUBLE_IS_ARM_MIXED_ENDIAN_IEEE754 - "Checking doubles are ARM mixed-endian IEEE 754 binary64" - ${check_src} - DIRECT - ) +# TODO: factorize this try_compile statement +try_compile(DOUBLE_BIG_ENDIAN_TEST_COMPILED + ${CMAKE_CURRENT_BINARY_DIR} + ${check_src} + COMPILE_DEFINITIONS ${CMAKE_REQUIRED_DEFINITIONS} + COMPILE_DEFINITIONS ${CMAKE_REQUIRED_DEFINITIONS} + CMAKE_FLAGS -DCOMPILE_DEFINITIONS:STRING=${MACRO_CHECK_FUNCTION_DEFINITIONS} + "${CHECK_C_SOURCE_COMPILES_ADD_LIBRARIES}" + "${CHECK_C_SOURCE_COMPILES_ADD_INCLUDES}" + COPY_FILE ${CMAKE_CURRENT_BINARY_DIR}/double_big_endian.bin) + +if(DOUBLE_BIG_ENDIAN_TEST_COMPILED) + file(READ ${CMAKE_CURRENT_BINARY_DIR}/double_big_endian.bin DOUBLE_BIG_ENDIAN_DATA) + string(FIND ${DOUBLE_BIG_ENDIAN_DATA} "noonsees" NOONSEES) + if(NOONSEES) + set(DOUBLE_IS_BIG_ENDIAN_IEEE754 1) + set(DOUBLE_IS_LITTLE_ENDIAN_IEEE754 0) + else() + string(FIND ${DOUBLE_BIG_ENDIAN_DATA} "seesnoon" SEESNOON) + if(SEESNOON) + set(DOUBLE_IS_BIG_ENDIAN_IEEE754 0) + set(DOUBLE_IS_LITTLE_ENDIAN_IEEE754 1) + else() + message(WARNING "Could not determine if double precision floats endianness") + endif() + endif() +endif() # The short float repr introduced in Python 3.1 requires the # correctly-rounded string <-> double conversion functions from diff --git a/cmake/Extensions.cmake b/cmake/Extensions.cmake index 45b63f236..c0edc2468 100644 --- a/cmake/Extensions.cmake +++ b/cmake/Extensions.cmake @@ -196,7 +196,7 @@ function(add_python_extension name) ) endif() - if(APPLE) + if(APPLE OR ANDROID) set_target_properties(${target_name} PROPERTIES LINK_FLAGS -Wl,-undefined,dynamic_lookup SUFFIX .so diff --git a/cmake/extensions/CMakeLists.txt b/cmake/extensions/CMakeLists.txt index 10750ccce..10f3245dd 100644 --- a/cmake/extensions/CMakeLists.txt +++ b/cmake/extensions/CMakeLists.txt @@ -373,16 +373,18 @@ add_python_extension(_xxtestfuzz _xxtestfuzz/fuzzer.c ) -# Python 3.8 -set(_wide_char_modifier "L") -add_python_extension(_testinternalcapi - REQUIRES - IS_PY3_8_OR_GREATER - SOURCES - _testinternalcapi.c - DEFINITIONS - "PY3_DLLNAME=${_wide_char_modifier}\"python3$<$:_d>\"" -) +if (NOT ANDROID) + # Python 3.8 + set(_wide_char_modifier "L") + add_python_extension(_testinternalcapi + REQUIRES + IS_PY3_8_OR_GREATER + SOURCES + _testinternalcapi.c + DEFINITIONS + "PY3_DLLNAME=${_wide_char_modifier}\"python3$<$:_d>\"" + ) +endif() # Python 3.9 add_python_extension(_peg_parser ALWAYS_BUILTIN @@ -417,9 +419,11 @@ add_python_extension(_xxsubinterpreters ${WIN32_BUILTIN} _xxsubinterpretersmodule.c ) -# UNIX-only extensions -add_python_extension(fcntl REQUIRES UNIX SOURCES fcntlmodule.c) -add_python_extension(grp REQUIRES UNIX SOURCES grpmodule.c) +if(NOT ANDROID) + # UNIX-only extensions + add_python_extension(fcntl REQUIRES UNIX SOURCES fcntlmodule.c) + add_python_extension(grp REQUIRES UNIX SOURCES grpmodule.c) +endif() set(nis_REQUIRES UNIX HAVE_LIBNSL) set(nis_LIBRARIES ${HAVE_LIBNSL}) @@ -834,6 +838,7 @@ elseif(${CMAKE_SIZEOF_VOID_P} EQUAL 4) if(HAVE_GCC_ASM_FOR_X87 AND (CMAKE_C_COMPILER_ID MATCHES "GNU" OR CMAKE_C_COMPILER_ID MATCHES "Clang") AND NOT CMAKE_SYSTEM MATCHES SunOS + AND NOT ANDROID ) # solaris: problems with register allocation. # icc >= 11.0 works as well. diff --git a/cmake/lib/CMakeLists.txt b/cmake/lib/CMakeLists.txt index ac97ab4b3..5f62ecab3 100644 --- a/cmake/lib/CMakeLists.txt +++ b/cmake/lib/CMakeLists.txt @@ -37,20 +37,22 @@ endforeach() # Generate grammar tables in install directory # XXX Should a custom target be added to generate file at built time ? -install(CODE "find_program( - PYTHON_EXECUTABLE python - HINTS \$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${BIN_INSTALL_DIR} - NO_DEFAULT_PATH) -set(wrapper) -if(UNIX) - set(_envvar LD_LIBRARY_PATH) - if(APPLE) - set(_envvar DYLD_LIBRARY_PATH) - endif() - set(wrapper env \${_envvar}=\$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${LIBPYTHON_LIBDIR}) +if(NOT ANDROID) + install(CODE "find_program( + PYTHON_EXECUTABLE python + HINTS \$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${BIN_INSTALL_DIR} + NO_DEFAULT_PATH) + set(wrapper) + if(UNIX) + set(_envvar LD_LIBRARY_PATH) + if(APPLE) + set(_envvar DYLD_LIBRARY_PATH) + endif() + set(wrapper env \${_envvar}=\$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${LIBPYTHON_LIBDIR}) + endif() + execute_process(COMMAND \${wrapper} \${PYTHON_EXECUTABLE} -m lib2to3.pgen2.driver + \$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${PYTHONHOME}/lib2to3/Grammar.txt) + execute_process(COMMAND \${wrapper} \${PYTHON_EXECUTABLE} -m lib2to3.pgen2.driver + \$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${PYTHONHOME}/lib2to3/PatternGrammar.txt) + ") endif() -execute_process(COMMAND \${wrapper} \${PYTHON_EXECUTABLE} -m lib2to3.pgen2.driver - \$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${PYTHONHOME}/lib2to3/Grammar.txt) -execute_process(COMMAND \${wrapper} \${PYTHON_EXECUTABLE} -m lib2to3.pgen2.driver - \$ENV{DESTDIR}\${CMAKE_INSTALL_PREFIX}/${PYTHONHOME}/lib2to3/PatternGrammar.txt) -") diff --git a/cmake/libpython/CMakeLists.txt b/cmake/libpython/CMakeLists.txt index c344b674f..b7124d3e5 100644 --- a/cmake/libpython/CMakeLists.txt +++ b/cmake/libpython/CMakeLists.txt @@ -744,6 +744,7 @@ set(LIBPYTHON_DEEPFREEZE_SOURCES ) if(PY_VERSION VERSION_GREATER_EQUAL "3.11") +if(NOT ANDROID) # Build _bootstrap_python executable add_executable(_bootstrap_python ${SRC_DIR}/Programs/_bootstrap_python.c @@ -763,6 +764,7 @@ target_compile_definitions(_bootstrap_python PUBLIC Py_NO_ENABLE_SHARED ) +endif() list(APPEND LIBPYTHON_DEEPFREEZE_SOURCES ${SRC_DIR}/Python/deepfreeze/deepfreeze.c @@ -773,7 +775,7 @@ set(DEEPFREEZE_PY ${SRC_DIR}/Tools/$,${BUILD_PYTHON},_bootstrap_python> ${DEEPFREEZE_PY} "${SRC_DIR}/Python/frozen_modules/importlib._bootstrap.h:importlib._bootstrap" "${SRC_DIR}/Python/frozen_modules/importlib._bootstrap_external.h:importlib._bootstrap_external" diff --git a/cmake/platform.c b/cmake/platform.c index 4c8278967..7530a33e3 100644 --- a/cmake/platform.c +++ b/cmake/platform.c @@ -18,16 +18,28 @@ char *PLATFORM_TRIPLET = #if defined(__linux__) # if defined(__x86_64__) && defined(__LP64__) +# if defined(__ANDROID_NDK__) + "x86_64-linux-android" +# else "x86_64-linux-gnu" +# endif # elif defined(__x86_64__) && defined(__ILP32__) "x86_64-linux-gnux32" # elif defined(__i386__) +# if defined(__ANDROID_NDK__) + "i686-linux-android" +# else "i386-linux-gnu" +# endif # elif defined(__aarch64__) && defined(__AARCH64EL__) # if defined(__ILP32__) "aarch64_ilp32-linux-gnu" # else +# if defined(__ANDROID_NDK__) + "aarch64-linux-android" +# else "aarch64-linux-gnu" +# endif # endif # elif defined(__aarch64__) && defined(__AARCH64EB__) # if defined(__ILP32__) @@ -45,7 +57,11 @@ char *PLATFORM_TRIPLET = # endif # elif defined(__ARM_EABI__) && !defined(__ARM_PCS_VFP) # if defined(__ARMEL__) +# if defined(__ANDROID_NDK__) + "arm-linux-androideabi" +# else "arm-linux-gnueabi" +# endif # else "armeb-linux-gnueabi" # endif diff --git a/cmake/python/CMakeLists.txt b/cmake/python/CMakeLists.txt index cfbe1a11d..60cda177a 100644 --- a/cmake/python/CMakeLists.txt +++ b/cmake/python/CMakeLists.txt @@ -47,7 +47,7 @@ if(WIN32) ) endif() -if(UNIX) +if(UNIX AND NOT ANDROID) # Setup landmark allowing to run the interpreter from a build tree. See 'getpath.c' for details. set(_sysconfigdata_py "_sysconfigdata.py") if("${PY_VERSION}" VERSION_GREATER_EQUAL "3.6.0")