App-Ariza.git | runner/ | CMakeLists.txt
cmake_minimum_required(VERSION 3.16)
# The compiled Windows launcher a bundle ships as bin/<exec>.exe, and the
# portable core it is built on.
#
# Two build shapes, on purpose:
#
# * On Windows (MSYS2 UCRT64 for x86_64, CLANGARM64 for aarch64) this
# builds the executable that gets published as a release artefact and
# pinned by resources/runner-checksums.txt. That is the only lane
# that produces something a bundle carries.
# * Everywhere else it builds the core and its tests, and nothing else:
# src/main_win32.c is not in the target list, and the file is
# #ifdef'd besides. The rules worth testing — the argv[0] boundary,
# the quoting, the sidecar grammar, the environment values — are all
# in the core, so `ctest` says something useful on a Mac or a Linux
# CI runner, which is where this repository's suite actually runs.
#
# MSVC is deliberately not a target. The runner is built by the same
# MSYS2 toolchains that build the notcurses packs a bundle carries, which
# keeps one C toolchain story for the whole Windows path.
project(ariza-runner
DESCRIPTION "Compiled launcher for ariza bundles on Windows"
LANGUAGES C)
option(ARIZA_RUNNER_BUILD_TESTS "Build the runner test suite" ON)
option(ARIZA_RUNNER_WERROR "Treat warnings as errors" OFF)
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
# Strict -std=c17 (C_EXTENSIONS OFF) makes glibc hide POSIX interfaces
# unless a feature-test macro asks for them; _DEFAULT_SOURCE /
# _DARWIN_C_SOURCE keep the glibc / macOS default namespaces intact
# alongside it. The core itself only needs <stdlib.h>, but the test
# harness prints, and the next thing added here should not have to
# rediscover this.
if(WIN32)
add_compile_definitions(UNICODE _UNICODE)
else()
add_compile_definitions(_POSIX_C_SOURCE=200809L _DEFAULT_SOURCE
_DARWIN_C_SOURCE)
endif()
set(ARIZA_RUNNER_C_WARNINGS -Wall -Wextra -Wshadow -Wvla)
if(ARIZA_RUNNER_WERROR)
list(APPEND ARIZA_RUNNER_C_WARNINGS -Werror)
endif()
add_library(ariza_runner_core STATIC
src/strings.c
src/config.c
src/env.c
src/cmdline.c
src/handoff.c)
target_include_directories(ariza_runner_core PUBLIC include)
set_target_properties(ariza_runner_core PROPERTIES
C_STANDARD 17 C_STANDARD_REQUIRED ON C_EXTENSIONS OFF)
target_compile_options(ariza_runner_core PRIVATE ${ARIZA_RUNNER_C_WARNINGS})
if(WIN32)
add_executable(ariza_runner src/main_win32.c)
target_link_libraries(ariza_runner PRIVATE ariza_runner_core)
target_link_libraries(ariza_runner PRIVATE bcrypt)
set_target_properties(ariza_runner PROPERTIES
C_STANDARD 17 C_STANDARD_REQUIRED ON C_EXTENSIONS OFF
# The release lanes rename this to
# ariza-runner-windows-<arch>.exe; a bundle then stages it as
# bin/<exec>.exe. ARIZA_RUNNER_OUTPUT_NAME lets the lane do
# the naming here instead of with a `mv`.
OUTPUT_NAME "${ARIZA_RUNNER_OUTPUT_NAME}")
if(NOT ARIZA_RUNNER_OUTPUT_NAME)
set_target_properties(ariza_runner PROPERTIES OUTPUT_NAME ariza-runner)
endif()
target_compile_options(ariza_runner PRIVATE ${ARIZA_RUNNER_C_WARNINGS})
# -municode gives wmain and a UTF-16 entry point. Both mingw-w64
# GCC (UCRT64) and clang's mingw driver (CLANGARM64) accept it, and
# it has to reach the link as well as the compile: it selects
# crt2u.o, which is what calls wmain rather than main.
target_compile_options(ariza_runner PRIVATE -municode)
target_link_options(ariza_runner PRIVATE -municode)
# -static, because this executable is copied into a bundle and run
# on machines that have never heard of MSYS2. Without it the link
# can pick up libgcc_s_seh-1.dll or libwinpthread-1.dll from the
# build environment, and the failure would be invisible everywhere
# it was tested and total on a user's machine — the same shape of
# bug as an MSVC-built dependency importing vcruntime140.dll. The
# release lane asserts the import table afterwards, because a
# compiler flag is a hope and the PE header is the fact.
target_link_options(ariza_runner PRIVATE -static)
endif()
if(ARIZA_RUNNER_BUILD_TESTS)
enable_testing()
add_library(ariza_runner_test_support STATIC tests/support.c)
target_link_libraries(ariza_runner_test_support PUBLIC ariza_runner_core)
target_include_directories(ariza_runner_test_support PUBLIC tests)
set_target_properties(ariza_runner_test_support PROPERTIES
C_STANDARD 17 C_STANDARD_REQUIRED ON C_EXTENSIONS OFF)
target_compile_options(ariza_runner_test_support PRIVATE
${ARIZA_RUNNER_C_WARNINGS})
# The committed rendering of the sidecar template, which
# tests/test_config.c parses with the real parser. An absolute path
# baked in at configure time, because ctest runs from the build
# directory and this is the one file the C suite shares with the
# Raku one.
get_filename_component(ARIZA_GOLDEN_SIDECAR
"${CMAKE_CURRENT_SOURCE_DIR}/../t/golden/launcher-windows-x86_64.ariza"
ABSOLUTE)
foreach(t IN ITEMS config env cmdline handoff)
add_executable(test_${t} tests/test_${t}.c)
target_compile_definitions(test_${t} PRIVATE
ARIZA_GOLDEN_SIDECAR="${ARIZA_GOLDEN_SIDECAR}")
target_link_libraries(test_${t} PRIVATE ariza_runner_test_support)
set_target_properties(test_${t} PROPERTIES
C_STANDARD 17 C_STANDARD_REQUIRED ON C_EXTENSIONS OFF)
target_compile_options(test_${t} PRIVATE ${ARIZA_RUNNER_C_WARNINGS})
add_test(NAME ${t} COMMAND test_${t})
endforeach()
endif()