Skip to content

Commit b566396

Browse files
committed
Use ExternalProject for downloading bison and re2c
This simplifies downloading, configuring etc. The Bison downloading and configuring for now works only for GNU Bison. Should be improved further.
1 parent ba15f0b commit b566396

File tree

9 files changed

+262
-210
lines changed

9 files changed

+262
-210
lines changed

cmake/cmake/Configuration.cmake

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -258,3 +258,6 @@ set_package_properties(
258258
URL "https://zlib.net/"
259259
DESCRIPTION "Compression library"
260260
)
261+
262+
# Set base directory for the ExternalProject CMake module across the PHP.
263+
set_directory_properties(PROPERTIES EP_BASE ${PHP_BINARY_DIR}/_deps/EP)

cmake/cmake/modules/FindBISON.cmake

Lines changed: 75 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,11 @@ See: https://cmake.org/cmake/help/latest/module/FindBISON.html
88
#]=============================================================================]
99

1010
include(FeatureSummary)
11+
include(FindPackageHandleStandardArgs)
12+
13+
################################################################################
14+
# Configuration.
15+
################################################################################
1116

1217
set_package_properties(
1318
BISON
@@ -18,8 +23,73 @@ set_package_properties(
1823

1924
# Find package with upstream CMake module; override CMAKE_MODULE_PATH to prevent
2025
# the maximum nesting/recursion depth error on some systems, like macOS.
21-
set(_php_cmake_module_path ${CMAKE_MODULE_PATH})
22-
unset(CMAKE_MODULE_PATH)
23-
include(FindBISON)
24-
set(CMAKE_MODULE_PATH ${_php_cmake_module_path})
25-
unset(_php_cmake_module_path)
26+
#set(_php_cmake_module_path ${CMAKE_MODULE_PATH})
27+
#unset(CMAKE_MODULE_PATH)
28+
#include(FindBISON)
29+
#set(CMAKE_MODULE_PATH ${_php_cmake_module_path})
30+
#unset(_php_cmake_module_path)
31+
32+
################################################################################
33+
# Find the executable.
34+
################################################################################
35+
36+
set(_reason "")
37+
38+
find_program(
39+
BISON_EXECUTABLE
40+
NAMES bison win-bison win_bison
41+
DOC "The path to the bison executable"
42+
)
43+
mark_as_advanced(BISON_EXECUTABLE)
44+
45+
if(NOT BISON_EXECUTABLE)
46+
string(APPEND _reason "The bison command-line executable not found. ")
47+
endif()
48+
49+
################################################################################
50+
# Check version.
51+
################################################################################
52+
53+
block(PROPAGATE BISON_VERSION _reason)
54+
if(CMAKE_VERSION VERSION_GREATER_EQUAL 3.29)
55+
set(test IS_EXECUTABLE)
56+
else()
57+
set(test EXISTS)
58+
endif()
59+
60+
if(${test} ${BISON_EXECUTABLE})
61+
execute_process(
62+
COMMAND ${BISON_EXECUTABLE} --version
63+
OUTPUT_VARIABLE version
64+
RESULT_VARIABLE result
65+
ERROR_QUIET
66+
OUTPUT_STRIP_TRAILING_WHITESPACE
67+
)
68+
69+
if(NOT result EQUAL 0)
70+
string(APPEND _reason "Command ${BISON_EXECUTABLE} --version failed. ")
71+
elseif(version)
72+
# Bison++
73+
if(version MATCHES "^bison\\+\\+ Version ([^,]+)")
74+
set(BISON_VERSION "${CMAKE_MATCH_1}")
75+
# GNU Bison
76+
elseif(version MATCHES "^bison \\(GNU Bison\\) ([^\n]+)\n")
77+
set(BISON_VERSION "${CMAKE_MATCH_1}")
78+
elseif(version MATCHES "^GNU Bison (version )?([^\n]+)")
79+
set(BISON_VERSION "${CMAKE_MATCH_2}")
80+
else()
81+
string(APPEND _reason "Invalid version format. ")
82+
endif()
83+
endif()
84+
endif()
85+
endblock()
86+
87+
find_package_handle_standard_args(
88+
BISON
89+
REQUIRED_VARS BISON_EXECUTABLE BISON_VERSION
90+
VERSION_VAR BISON_VERSION
91+
HANDLE_VERSION_RANGE
92+
REASON_FAILURE_MESSAGE "${_reason}"
93+
)
94+
95+
unset(_reason)

cmake/cmake/modules/FindRE2C.cmake

Lines changed: 4 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@ set_package_properties(
2828
)
2929

3030
################################################################################
31-
# Find re2c.
31+
# Find the executable.
3232
################################################################################
3333

3434
set(_reason "")
@@ -59,25 +59,20 @@ block(PROPAGATE RE2C_VERSION _reason)
5959
execute_process(
6060
COMMAND ${RE2C_EXECUTABLE} --version
6161
OUTPUT_VARIABLE version
62-
ERROR_VARIABLE error
6362
RESULT_VARIABLE result
63+
ERROR_QUIET
6464
OUTPUT_STRIP_TRAILING_WHITESPACE
65-
ERROR_STRIP_TRAILING_WHITESPACE
6665
)
6766

6867
if(NOT result EQUAL 0)
69-
string(
70-
APPEND
71-
_reason
72-
"Command \"${RE2C_EXECUTABLE} --version\" failed:\n${error} "
73-
)
68+
string(APPEND _reason "Command \"${RE2C_EXECUTABLE} --version\" failed. ")
7469
elseif(version MATCHES "^re2c ([0-9.]+[^\n]+)")
7570
find_package_check_version("${CMAKE_MATCH_1}" valid)
7671
if(valid)
7772
set(RE2C_VERSION "${CMAKE_MATCH_1}")
7873
endif()
7974
else()
80-
string(APPEND _reason "Invalid version format:\n${version} ")
75+
string(APPEND _reason "Invalid version format. ")
8176
endif()
8277
endif()
8378
endblock()

cmake/cmake/modules/PHP/Bison.cmake

Lines changed: 44 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -5,10 +5,6 @@ Generate parser-related files with Bison. This module includes common `bison`
55
configuration with minimum required version and common settings across the
66
PHP build.
77
8-
When `bison` cannot be found on the system or the found version is not suitable,
9-
this module can also download and build it from its Git repository sources
10-
release archive as part of the project build.
11-
128
## Configuration variables
139
1410
These variables can be set before including this module
@@ -18,18 +14,16 @@ These variables can be set before including this module
1814
BISON package with `find_package(BISON <version-constraint> ...)` in this
1915
module.
2016
17+
* `PHP_BISON_DOWNLOAD_VERSION` - When Bison cannot be found on the system or the
18+
found version is not suitable, this module can also download and build it from
19+
its release archive sources as part of the project build. Set which Bison
20+
version should be downloaded.
21+
2122
* `PHP_BISON_OPTIONS` - A semicolon-separated list of default Bison options.
2223
This module sets some sensible defaults. When `php_bison(APPEND)` is used, the
2324
options specified in the `php_bison(OPTIONS <options>...)` are appended to
2425
these default global options.
2526
26-
* `PHP_BISON_DISABLE_DOWNLOAD` - Set to `TRUE` to disable downloading and
27-
building bison package from source, when it is not found on the system or
28-
found version is not suitable.
29-
30-
* `PHP_BISON_DOWNLOAD_VERSION` - Override the default `bison` version to be
31-
downloaded when not found on the system.
32-
3327
* `PHP_BISON_WORKING_DIRECTORY` - Set the default global working directory
3428
(`WORKING_DIRECTORY <dir>` option) for all `php_bison()` invocations in the
3529
scope of the current directory.
@@ -266,14 +260,13 @@ php_bison(foo parser.y parser.c OPTIONS $<$<CONFIG:Debug>:--debug> --yacc)
266260

267261
include_guard(GLOBAL)
268262

269-
include(FetchContent)
270263
include(FeatureSummary)
271264

272265
################################################################################
273266
# Configuration.
274267
################################################################################
275268

276-
macro(_php_bison_config)
269+
macro(php_bison_config)
277270
# Minimum required bison version.
278271
if(NOT PHP_BISON_VERSION)
279272
set(PHP_BISON_VERSION 3.0.0)
@@ -365,7 +358,7 @@ function(php_bison name input output)
365358
set(outputs ${output})
366359
set(extraOutputs "")
367360

368-
_php_bison_config()
361+
php_bison_config()
369362
_php_bison_process_header_file()
370363
_php_bison_set_package_properties()
371364

@@ -375,12 +368,15 @@ function(php_bison name input output)
375368
set(quiet "QUIET")
376369
endif()
377370

378-
find_package(BISON ${PHP_BISON_VERSION} GLOBAL ${quiet})
371+
if(NOT TARGET Bison::Bison)
372+
find_package(BISON ${PHP_BISON_VERSION} GLOBAL ${quiet})
373+
endif()
379374

380375
if(
381376
NOT BISON_FOUND
382-
AND NOT PHP_BISON_DISABLE_DOWNLOAD
377+
AND PHP_BISON_DOWNLOAD_VERSION
383378
AND packageType STREQUAL "REQUIRED"
379+
AND NOT CMAKE_SCRIPT_MODE_FILE
384380
)
385381
_php_bison_download()
386382
endif()
@@ -436,7 +432,6 @@ function(php_bison name input output)
436432
${input}
437433
${parsed_DEPENDS}
438434
$<TARGET_NAME_IF_EXISTS:Bison::Bison>
439-
$<TARGET_NAME_IF_EXISTS:bison>
440435
COMMENT "${message}"
441436
VERBATIM
442437
COMMAND_EXPAND_LISTS
@@ -698,53 +693,49 @@ function(_php_bison_get_commands result)
698693
return(PROPAGATE ${result})
699694
endfunction()
700695

701-
################################################################################
702-
# Download and build bison if not found.
703-
################################################################################
704-
696+
# Download and build Bison if not found.
705697
function(_php_bison_download)
706698
set(BISON_VERSION ${PHP_BISON_DOWNLOAD_VERSION})
699+
set(BISON_FOUND TRUE)
707700

708-
message(STATUS "Downloading bison ${BISON_VERSION}")
709-
FetchContent_Populate(
710-
BISON
711-
URL https://ftp.gnu.org/gnu/bison/bison-${BISON_VERSION}.tar.gz
712-
SOURCE_DIR ${CMAKE_BINARY_DIR}/_deps/bison
713-
)
701+
if(TARGET Bison::Bison)
702+
return(PROPAGATE BISON_FOUND BISON_VERSION)
703+
endif()
714704

715-
message(STATUS "Configuring Bison ${BISON_VERSION}")
716-
execute_process(
717-
COMMAND ./configure
718-
OUTPUT_VARIABLE result
719-
ECHO_OUTPUT_VARIABLE
720-
WORKING_DIRECTORY ${CMAKE_BINARY_DIR}/_deps/bison
721-
)
705+
message(STATUS "Bison ${BISON_VERSION} will be downloaded at build phase")
706+
707+
include(ExternalProject)
722708

723-
message(STATUS "Building Bison ${BISON_VERSION}")
724-
include(ProcessorCount)
725-
processorcount(processors)
726-
execute_process(
727-
COMMAND ${CMAKE_MAKE_PROGRAM} -j${processors}
728-
OUTPUT_VARIABLE result
729-
ECHO_OUTPUT_VARIABLE
730-
WORKING_DIRECTORY ${CMAKE_BINARY_DIR}/_deps/bison
709+
ExternalProject_Add(
710+
bison
711+
URL https://ftp.gnu.org/gnu/bison/bison-${BISON_VERSION}.tar.gz
712+
DOWNLOAD_EXTRACT_TIMESTAMP TRUE
713+
CONFIGURE_COMMAND
714+
<SOURCE_DIR>/configure
715+
--prefix=<INSTALL_DIR>
716+
--enable-silent-rules
717+
--disable-yacc
718+
--disable-dependency-tracking
719+
LOG_INSTALL TRUE
731720
)
732721

733-
set(BISON_FOUND TRUE)
722+
# Set bison executable.
723+
ExternalProject_Get_Property(bison INSTALL_DIR)
724+
set_property(CACHE BISON_EXECUTABLE PROPERTY VALUE ${INSTALL_DIR}/bin/bison)
734725

735-
set_property(
736-
CACHE BISON_EXECUTABLE
737-
PROPERTY VALUE ${CMAKE_BINARY_DIR}/_deps/bison/src/bison
726+
add_executable(Bison::Bison IMPORTED GLOBAL)
727+
set_target_properties(
728+
Bison::Bison
729+
PROPERTIES IMPORTED_LOCATION ${BISON_EXECUTABLE}
738730
)
731+
add_dependencies(Bison::Bison bison)
739732

740733
# Move dependency to PACKAGES_FOUND.
741-
block()
742-
get_property(packagesNotFound GLOBAL PROPERTY PACKAGES_NOT_FOUND)
743-
list(REMOVE_ITEM packagesNotFound BISON)
744-
set_property(GLOBAL PROPERTY PACKAGES_NOT_FOUND packagesNotFound)
745-
get_property(packagesFound GLOBAL PROPERTY PACKAGES_FOUND)
746-
set_property(GLOBAL APPEND PROPERTY PACKAGES_FOUND BISON)
747-
endblock()
734+
get_property(packagesNotFound GLOBAL PROPERTY PACKAGES_NOT_FOUND)
735+
list(REMOVE_ITEM packagesNotFound BISON)
736+
set_property(GLOBAL PROPERTY PACKAGES_NOT_FOUND packagesNotFound)
737+
get_property(packagesFound GLOBAL PROPERTY PACKAGES_FOUND)
738+
set_property(GLOBAL APPEND PROPERTY PACKAGES_FOUND BISON)
748739

749740
return(PROPAGATE BISON_FOUND BISON_VERSION)
750741
endfunction()

0 commit comments

Comments
 (0)