1
1
#[=============================================================================[
2
2
# PHP/StandardLibrary
3
3
4
- This module determines the C standard library used for the build:
4
+ This module determines the C standard library used for the build.
5
+
6
+ Load this module in a CMake project with:
5
7
6
8
```cmake
7
9
include(PHP/StandardLibrary)
8
10
```
9
11
10
- ## Cache variables
12
+ ## Variables
13
+
14
+ Including this module will define the following variables:
15
+
16
+ ### Cache variables
11
17
12
18
* `PHP_C_STANDARD_LIBRARY`
13
19
14
- Lowercase name of the C standard library:
20
+ Lowercase name of the C standard library. This internal cache variable will be
21
+ set to one of the following values:
15
22
16
23
* `cosmopolitan`
17
24
* `dietlibc`
@@ -20,135 +27,201 @@ include(PHP/StandardLibrary)
20
27
* `mscrt`
21
28
* `musl`
22
29
* `uclibc`
30
+ * "" (empty string)
31
+
32
+ If C standard library cannot be determined, it is set to empty string.
33
+
34
+ ### Result variables:
23
35
24
- If library cannot be determined, it is set to empty string.
36
+ * `PHP_C_STANDARD_LIBRARY_CODE`
25
37
26
- * `__MUSL__` - Whether the C standard library is musl.
38
+ CMake variable containing some helper code for use in the C configuration
39
+ header.
40
+
41
+ For example, when C standard library implementation is musl, the value of this
42
+ variable will contain:
43
+
44
+ ```c
45
+ /* Define to 1 when using musl libc. */
46
+ #define __MUSL__ 1
47
+ ```
27
48
28
49
## Examples
29
50
30
51
Basic usage:
31
52
32
53
```cmake
33
54
# CMakeLists.txt
55
+
34
56
include(PHP/StandardLibrary)
57
+
58
+ message(STATUS "PHP_C_STANDARD_LIBRARY=${PHP_C_STANDARD_LIBRARY}")
59
+
60
+ file(CONFIGURE OUTPUT config.h CONTENT [[
61
+ @PHP_C_STANDARD_LIBRARY_CODE@
62
+ ]])
35
63
```
36
64
#]=============================================================================]
37
65
38
- include_guard (GLOBAL )
39
-
40
- if (DEFINED PHP_C_STANDARD_LIBRARY)
66
+ # Skip in consecutive configuration phases and set configuration header code for
67
+ # consecutive module inclusions, if needed.
68
+ if (COMMAND _php_standard_library_get_code)
69
+ _php_standard_library_get_code(PHP_C_STANDARD_LIBRARY_CODE)
41
70
return ()
42
71
endif ()
43
72
73
+ include_guard (GLOBAL )
74
+
44
75
include (CheckSymbolExists)
45
76
include (CMakePushCheckState)
46
77
47
- set (PHP_C_STANDARD_LIBRARY "" CACHE INTERNAL "The C standard library." )
48
-
49
- message (CHECK_START "Checking C standard library" )
78
+ function (_php_standard_library_get_code result)
79
+ string (
80
+ CONCAT
81
+ ${result}
82
+ "/* Define to 1 when using musl libc. */\n "
83
+ "#cmakedefine __MUSL__ 1\n "
84
+ )
85
+
86
+ if (PHP_C_STANDARD_LIBRARY STREQUAL "musl" )
87
+ set (__MUSL__ TRUE )
88
+ else ()
89
+ set (__MUSL__ FALSE )
90
+ endif ()
91
+
92
+ string (CONFIGURE "${${result} }" ${result} @ONLY)
93
+
94
+ return (PROPAGATE ${result} )
95
+ endfunction ()
96
+
97
+ function (_php_standard_library_check)
98
+ unset (PHP_C_STANDARD_LIBRARY)
99
+ unset (PHP_C_STANDARD_LIBRARY CACHE )
100
+
101
+ # The MS C runtime library (CRT).
102
+ if (MSVC )
103
+ set (PHP_C_STANDARD_LIBRARY "mscrt" )
104
+ elseif (CMAKE_SYSTEM_NAME STREQUAL "Windows" )
105
+ check_symbol_exists(_MSC_VER stdio.h PHP_C_STANDARD_LIBRARY)
106
+ endif ()
107
+ if (PHP_C_STANDARD_LIBRARY)
108
+ set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "mscrt" )
109
+ return ()
110
+ endif ()
111
+
112
+ unset (PHP_C_STANDARD_LIBRARY CACHE )
113
+
114
+ # The uClibc and its maintained fork uClibc-ng behave like minimalistic GNU C
115
+ # library but have differences. They can be determined by the __UCLIBC__
116
+ # symbol and must be checked first because they also define the __GLIBC__
117
+ # symbol.
118
+ check_symbol_exists(__UCLIBC__ features.h PHP_C_STANDARD_LIBRARY)
119
+ if (PHP_C_STANDARD_LIBRARY)
120
+ set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "uclibc" )
121
+ return ()
122
+ endif ()
123
+
124
+ unset (PHP_C_STANDARD_LIBRARY CACHE )
125
+
126
+ # The diet libc.
127
+ check_symbol_exists(__dietlibc__ features.h PHP_C_STANDARD_LIBRARY)
128
+ if (PHP_C_STANDARD_LIBRARY)
129
+ set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "dietlibc" )
130
+ return ()
131
+ endif ()
132
+
133
+ unset (PHP_C_STANDARD_LIBRARY CACHE )
134
+
135
+ # The Cosmopolitan Libc.
136
+ check_symbol_exists(__COSMOPOLITAN__ "" PHP_C_STANDARD_LIBRARY)
137
+ if (PHP_C_STANDARD_LIBRARY)
138
+ set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "cosmopolitan" )
139
+ return ()
140
+ endif ()
141
+
142
+ unset (PHP_C_STANDARD_LIBRARY CACHE )
143
+
144
+ # The GNU C standard library has __GLIBC__ and __GLIBC_MINOR__ symbols since
145
+ # the very early version 2.0.
146
+ check_symbol_exists(__GLIBC__ features.h PHP_C_STANDARD_LIBRARY)
147
+ if (PHP_C_STANDARD_LIBRARY)
148
+ set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "glibc" )
149
+ return ()
150
+ endif ()
151
+
152
+ unset (PHP_C_STANDARD_LIBRARY CACHE )
153
+
154
+ # The LLVM libc.
155
+ check_symbol_exists(__LLVM_LIBC__ features.h PHP_C_STANDARD_LIBRARY)
156
+ if (PHP_C_STANDARD_LIBRARY)
157
+ set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "llvm" )
158
+ return ()
159
+ endif ()
160
+
161
+ unset (PHP_C_STANDARD_LIBRARY CACHE )
162
+
163
+ # The musl libc doesn't advertise itself with symbols, so it must be
164
+ # determined heuristically.
165
+ check_symbol_exists(__DEFINED_va_list stdarg.h PHP_C_STANDARD_LIBRARY)
166
+ if (PHP_C_STANDARD_LIBRARY)
167
+ set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "musl" )
168
+ return ()
169
+ endif ()
170
+
171
+ unset (PHP_C_STANDARD_LIBRARY CACHE )
50
172
51
- # The MS C runtime library (CRT).
52
- if (MSVC )
53
- set (_PHP_C_STANDARD_LIBRARY_MSCRT TRUE )
54
- elseif (CMAKE_SYSTEM_NAME STREQUAL "Windows" )
173
+ # Otherwise, try determining musl libc with ldd.
174
+ execute_process (
175
+ COMMAND ldd --version
176
+ OUTPUT_VARIABLE version
177
+ ERROR_QUIET
178
+ OUTPUT_STRIP_TRAILING_WHITESPACE
179
+ )
180
+
181
+ if (version MATCHES ".*musl libc.*" )
182
+ set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "musl" )
183
+ return ()
184
+ endif ()
185
+
186
+ set (PHP_C_STANDARD_LIBRARY "" CACHE INTERNAL "" )
187
+ endfunction ()
188
+
189
+ function (_php_standard_library)
190
+ # Skip in consecutive runs.
191
+ if (DEFINED PHP_C_STANDARD_LIBRARY)
192
+ return ()
193
+ endif ()
194
+
195
+ message (CHECK_START "Checking C standard library" )
55
196
cmake_push_check_state(RESET)
56
197
set (CMAKE_REQUIRED_QUIET TRUE )
57
- check_symbol_exists(_MSC_VER stdio.h _PHP_C_STANDARD_LIBRARY_MSCRT )
198
+ _php_standard_library_check( )
58
199
cmake_pop_check_state()
59
- endif ()
60
- if (_PHP_C_STANDARD_LIBRARY_MSCRT)
61
- set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "mscrt" )
62
- message (CHECK_PASS "MS C runtime library (CRT)" )
63
- return ()
64
- endif ()
65
-
66
- # The uClibc and its maintained fork uClibc-ng behave like minimalistic GNU C
67
- # library but have differences. They can be determined by the __UCLIBC__ symbol
68
- # and must be checked first because they also define the __GLIBC__ symbol.
69
- cmake_push_check_state(RESET)
70
- set (CMAKE_REQUIRED_QUIET TRUE )
71
- check_symbol_exists(__UCLIBC__ features.h _PHP_C_STANDARD_LIBRARY_UCLIBC)
72
- cmake_pop_check_state()
73
- if (_PHP_C_STANDARD_LIBRARY_UCLIBC)
74
- set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "uclibc" )
75
- message (CHECK_PASS "uClibc" )
76
- return ()
77
- endif ()
78
-
79
- # The diet libc.
80
- cmake_push_check_state(RESET)
81
- set (CMAKE_REQUIRED_QUIET TRUE )
82
- check_symbol_exists(__dietlibc__ features.h _PHP_C_STANDARD_LIBRARY_DIETLIBC)
83
- cmake_pop_check_state()
84
- if (_PHP_C_STANDARD_LIBRARY_DIETLIBC)
85
- set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "dietlibc" )
86
- message (CHECK_PASS "diet libc" )
87
- return ()
88
- endif ()
89
-
90
- # The Cosmopolitan Libc.
91
- cmake_push_check_state(RESET)
92
- set (CMAKE_REQUIRED_QUIET TRUE )
93
- check_symbol_exists(__COSMOPOLITAN__ "" _PHP_C_STANDARD_LIBRARY_COSMOPOLITAN)
94
- cmake_pop_check_state()
95
- if (_PHP_C_STANDARD_LIBRARY_COSMOPOLITAN)
96
- set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "cosmopolitan" )
97
- message (CHECK_PASS "Cosmopolitan Libc" )
98
- return ()
99
- endif ()
100
-
101
- # The GNU C standard library has __GLIBC__ and __GLIBC_MINOR__ symbols since the
102
- # very early version 2.0.
103
- cmake_push_check_state(RESET)
104
- set (CMAKE_REQUIRED_QUIET TRUE )
105
- check_symbol_exists(__GLIBC__ features.h _PHP_C_STANDARD_LIBRARY_GLIBC)
106
- cmake_pop_check_state()
107
- if (_PHP_C_STANDARD_LIBRARY_GLIBC)
108
- set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "glibc" )
109
- message (CHECK_PASS "GNU C (glibc)" )
110
- return ()
111
- endif ()
112
-
113
- # The LLVM libc.
114
- cmake_push_check_state(RESET)
115
- set (CMAKE_REQUIRED_QUIET TRUE )
116
- check_symbol_exists(__LLVM_LIBC__ features.h _PHP_C_STANDARD_LIBRARY_LLVM)
117
- cmake_pop_check_state()
118
- if (_PHP_C_STANDARD_LIBRARY_LLVM)
119
- set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "llvm" )
120
- message (CHECK_PASS "LLVM libc" )
121
- return ()
122
- endif ()
123
-
124
- # The musl libc doesn't advertise itself with symbols, so it must be determined
125
- # heuristically.
126
- cmake_push_check_state(RESET)
127
- set (CMAKE_REQUIRED_QUIET TRUE )
128
- check_symbol_exists(__DEFINED_va_list stdarg.h _PHP_C_STANDARD_LIBRARY_MUSL)
129
- cmake_pop_check_state()
130
- if (_PHP_C_STANDARD_LIBRARY_MUSL)
131
- set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "musl" )
132
- else ()
133
- # Otherwise, try determining musl libc with ldd.
134
- block()
135
- execute_process (
136
- COMMAND ldd --version
137
- OUTPUT_VARIABLE version
138
- ERROR_QUIET
139
- OUTPUT_STRIP_TRAILING_WHITESPACE
140
- )
141
-
142
- if (version MATCHES ".*musl libc.*" )
143
- set_property (CACHE PHP_C_STANDARD_LIBRARY PROPERTY VALUE "musl" )
144
- endif ()
145
- endblock()
146
- endif ()
147
- if (PHP_C_STANDARD_LIBRARY STREQUAL "musl" )
148
- set (__MUSL__ TRUE CACHE INTERNAL "Whether the C standard library is musl." )
149
- message (CHECK_PASS "musl" )
150
- return ()
151
- endif ()
152
200
153
- # Instead of an "unknown", output a common "libc" result.
154
- message (CHECK_FAIL "libc" )
201
+ if (PHP_C_STANDARD_LIBRARY STREQUAL "mscrt" )
202
+ message (CHECK_PASS "MS C runtime library (CRT)" )
203
+ elseif (PHP_C_STANDARD_LIBRARY STREQUAL "uclibc" )
204
+ message (CHECK_PASS "uClibc" )
205
+ elseif (PHP_C_STANDARD_LIBRARY STREQUAL "dietlibc" )
206
+ message (CHECK_PASS "diet libc" )
207
+ elseif (PHP_C_STANDARD_LIBRARY STREQUAL "cosmopolitan" )
208
+ message (CHECK_PASS "Cosmopolitan Libc" )
209
+ elseif (PHP_C_STANDARD_LIBRARY STREQUAL "glibc" )
210
+ message (CHECK_PASS "GNU C (glibc)" )
211
+ elseif (PHP_C_STANDARD_LIBRARY STREQUAL "llvm" )
212
+ message (CHECK_PASS "LLVM libc" )
213
+ elseif (PHP_C_STANDARD_LIBRARY STREQUAL "musl" )
214
+ message (CHECK_PASS "musl libc" )
215
+ else ()
216
+ # Instead of an "unknown", output a common "libc" result message.
217
+ message (CHECK_FAIL "libc" )
218
+ endif ()
219
+
220
+ set_property (
221
+ CACHE PHP_C_STANDARD_LIBRARY
222
+ PROPERTY HELPSTRING "The C standard library."
223
+ )
224
+ endfunction ()
225
+
226
+ _php_standard_library()
227
+ _php_standard_library_get_code(PHP_C_STANDARD_LIBRARY_CODE)
0 commit comments