re2 2.9.0 → 2.27.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/Gemfile +6 -0
- data/README.md +130 -22
- data/Rakefile +52 -90
- data/dependencies.yml +4 -4
- data/ext/re2/extconf.rb +256 -290
- data/ext/re2/re2.cc +1037 -318
- data/ext/re2/recipes.rb +24 -21
- data/lib/re2/regexp.rb +2 -0
- data/lib/re2/scanner.rb +2 -0
- data/lib/re2/string.rb +8 -6
- data/lib/re2/version.rb +1 -1
- data/lib/re2.rb +2 -0
- data/ports/archives/20260107.1.tar.gz +0 -0
- data/ports/archives/re2-2025-11-05.tar.gz +0 -0
- data/re2.gemspec +6 -4
- data/spec/kernel_spec.rb +2 -0
- data/spec/re2/match_data_spec.rb +520 -5
- data/spec/re2/regexp_spec.rb +342 -0
- data/spec/re2/scanner_spec.rb +185 -15
- data/spec/re2/set_spec.rb +123 -6
- data/spec/re2/string_spec.rb +2 -0
- data/spec/re2_spec.rb +219 -43
- data/spec/spec_helper.rb +2 -0
- metadata +17 -21
- data/ports/archives/20240116.1.tar.gz +0 -0
- data/ports/archives/re2-2024-03-01.tar.gz +0 -0
data/ext/re2/extconf.rb
CHANGED
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
1
3
|
# re2 (https://github.com/mudge/re2)
|
|
2
4
|
# Ruby bindings to RE2, a "fast, safe, thread-friendly alternative to
|
|
3
5
|
# backtracking regular expression engines like those used in PCRE, Perl, and
|
|
@@ -9,370 +11,334 @@
|
|
|
9
11
|
require 'mkmf'
|
|
10
12
|
require_relative 'recipes'
|
|
11
13
|
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
--enable-system-libraries
|
|
18
|
-
Use system libraries instead of building and using the packaged libraries.
|
|
19
|
-
|
|
20
|
-
--disable-system-libraries
|
|
21
|
-
Use the packaged libraries, and ignore the system libraries. This is the default.
|
|
22
|
-
|
|
14
|
+
module RE2
|
|
15
|
+
class Extconf
|
|
16
|
+
def configure
|
|
17
|
+
configure_cross_compiler
|
|
23
18
|
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
Look for re2 headers and library in DIRECTORY.
|
|
19
|
+
if config_system_libraries?
|
|
20
|
+
build_with_system_libraries
|
|
21
|
+
else
|
|
22
|
+
build_with_vendored_libraries
|
|
23
|
+
end
|
|
30
24
|
|
|
25
|
+
build_extension
|
|
31
26
|
|
|
32
|
-
|
|
27
|
+
create_makefile("re2")
|
|
28
|
+
end
|
|
33
29
|
|
|
34
|
-
|
|
35
|
-
|
|
30
|
+
def print_help
|
|
31
|
+
print(<<~TEXT)
|
|
32
|
+
USAGE: ruby #{$0} [options]
|
|
36
33
|
|
|
34
|
+
Flags that are always valid:
|
|
37
35
|
|
|
38
|
-
|
|
36
|
+
--enable-system-libraries
|
|
37
|
+
Use system libraries instead of building and using the packaged libraries.
|
|
39
38
|
|
|
40
|
-
|
|
41
|
-
|
|
39
|
+
--disable-system-libraries
|
|
40
|
+
Use the packaged libraries, and ignore the system libraries. This is the default.
|
|
42
41
|
|
|
43
|
-
CPPFLAGS
|
|
44
|
-
If this string is accepted by the C preprocessor, add it to the flags passed to the C preprocessor
|
|
45
42
|
|
|
46
|
-
|
|
47
|
-
If this string is accepted by the compiler, add it to the flags passed to the compiler
|
|
43
|
+
Flags only used when using system libraries:
|
|
48
44
|
|
|
49
|
-
|
|
50
|
-
If this string is accepted by the linker, add it to the flags passed to the linker
|
|
45
|
+
Related to re2 library:
|
|
51
46
|
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
HELP
|
|
47
|
+
--with-re2-dir=DIRECTORY
|
|
48
|
+
Look for re2 headers and library in DIRECTORY.
|
|
55
49
|
|
|
56
|
-
#
|
|
57
|
-
# utility functions
|
|
58
|
-
#
|
|
59
|
-
def config_system_libraries?
|
|
60
|
-
enable_config("system-libraries", ENV.key?('RE2_USE_SYSTEM_LIBRARIES'))
|
|
61
|
-
end
|
|
62
50
|
|
|
63
|
-
|
|
64
|
-
enable_config("cross-build")
|
|
65
|
-
end
|
|
51
|
+
Flags only used when building and using the packaged libraries:
|
|
66
52
|
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
end
|
|
53
|
+
--enable-cross-build
|
|
54
|
+
Enable cross-build mode. (You probably do not want to set this manually.)
|
|
70
55
|
|
|
71
|
-
def do_help
|
|
72
|
-
print(RE2_HELP_MESSAGE)
|
|
73
|
-
exit!(0)
|
|
74
|
-
end
|
|
75
56
|
|
|
76
|
-
|
|
77
|
-
RbConfig::CONFIG["target_os"].include?("darwin")
|
|
78
|
-
end
|
|
57
|
+
Environment variables used:
|
|
79
58
|
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
end
|
|
59
|
+
CC
|
|
60
|
+
Use this path to invoke the compiler instead of `RbConfig::CONFIG['CC']`
|
|
83
61
|
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
end
|
|
62
|
+
CPPFLAGS
|
|
63
|
+
If this string is accepted by the C preprocessor, add it to the flags passed to the C preprocessor
|
|
87
64
|
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
# prefer i686 (what external dev tools use) to i386 (what ruby's configure.ac emits).
|
|
91
|
-
host = RbConfig::CONFIG["host_alias"].empty? ? RbConfig::CONFIG["host"] : RbConfig::CONFIG["host_alias"]
|
|
92
|
-
host.gsub(/i386/, "i686")
|
|
93
|
-
end
|
|
65
|
+
CFLAGS
|
|
66
|
+
If this string is accepted by the compiler, add it to the flags passed to the compiler
|
|
94
67
|
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
end
|
|
68
|
+
LDFLAGS
|
|
69
|
+
If this string is accepted by the linker, add it to the flags passed to the linker
|
|
98
70
|
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
yield
|
|
71
|
+
LIBS
|
|
72
|
+
Add this string to the flags passed to the linker
|
|
73
|
+
TEXT
|
|
103
74
|
end
|
|
104
|
-
end
|
|
105
|
-
end
|
|
106
|
-
|
|
107
|
-
#
|
|
108
|
-
# main
|
|
109
|
-
#
|
|
110
|
-
do_help if arg_config('--help')
|
|
111
|
-
|
|
112
|
-
if ENV["CC"]
|
|
113
|
-
RbConfig::MAKEFILE_CONFIG["CC"] = ENV["CC"]
|
|
114
|
-
RbConfig::CONFIG["CC"] = ENV["CC"]
|
|
115
|
-
end
|
|
116
|
-
|
|
117
|
-
if ENV["CXX"]
|
|
118
|
-
RbConfig::MAKEFILE_CONFIG["CXX"] = ENV["CXX"]
|
|
119
|
-
RbConfig::CONFIG["CXX"] = ENV["CXX"]
|
|
120
|
-
end
|
|
121
75
|
|
|
122
|
-
|
|
123
|
-
# Enable optional warnings but disable deprecated register warning for Ruby 2.6 support
|
|
124
|
-
$CFLAGS << " -Wall -Wextra -funroll-loops"
|
|
125
|
-
$CPPFLAGS << " -Wno-register"
|
|
76
|
+
private
|
|
126
77
|
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
78
|
+
def configure_cross_compiler
|
|
79
|
+
RbConfig::CONFIG["CC"] = RbConfig::MAKEFILE_CONFIG["CC"] = ENV["CC"] if ENV["CC"]
|
|
80
|
+
RbConfig::CONFIG["CXX"] = RbConfig::MAKEFILE_CONFIG["CXX"] = ENV["CXX"] if ENV["CXX"]
|
|
81
|
+
end
|
|
130
82
|
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
83
|
+
def build_with_system_libraries
|
|
84
|
+
header_dirs = [
|
|
85
|
+
"/usr/local/include",
|
|
86
|
+
"/opt/homebrew/include",
|
|
87
|
+
"/usr/include"
|
|
88
|
+
]
|
|
134
89
|
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
90
|
+
lib_dirs = [
|
|
91
|
+
"/usr/local/lib",
|
|
92
|
+
"/opt/homebrew/lib",
|
|
93
|
+
"/usr/lib"
|
|
94
|
+
]
|
|
138
95
|
|
|
139
|
-
|
|
140
|
-
#include <re2/re2.h>
|
|
141
|
-
int main() { return 0; }
|
|
142
|
-
SRC
|
|
96
|
+
dir_config("re2", header_dirs, lib_dirs)
|
|
143
97
|
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
end
|
|
147
|
-
|
|
148
|
-
if re2_requires_version_flag
|
|
149
|
-
# Recent versions of re2 depend directly on abseil, which requires a
|
|
150
|
-
# compiler with C++14 support (see
|
|
151
|
-
# https://github.com/abseil/abseil-cpp/issues/1127 and
|
|
152
|
-
# https://github.com/abseil/abseil-cpp/issues/1431). However, the
|
|
153
|
-
# `std=c++14` flag doesn't appear to suffice; we need at least
|
|
154
|
-
# `std=c++17`.
|
|
155
|
-
abort "Cannot compile re2 with your compiler: recent versions require C++14 support." unless %w[c++20 c++17 c++11 c++0x].any? do |std|
|
|
156
|
-
checking_for("re2 that compiles with #{std} standard") do
|
|
157
|
-
if try_compile(minimal_program, compile_options + " -std=#{std}")
|
|
158
|
-
compile_options << " -std=#{std}"
|
|
159
|
-
$CPPFLAGS << " -std=#{std}"
|
|
160
|
-
|
|
161
|
-
true
|
|
162
|
-
end
|
|
98
|
+
unless have_library("re2")
|
|
99
|
+
abort "You must have re2 installed and specified with --with-re2-dir, please see https://github.com/google/re2/wiki/Install"
|
|
163
100
|
end
|
|
164
101
|
end
|
|
165
|
-
end
|
|
166
102
|
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
# generic Match() function.
|
|
170
|
-
#
|
|
171
|
-
# To test for this, try to compile a simple program that uses
|
|
172
|
-
# the newer form of Match() and set a flag if it is successful.
|
|
173
|
-
checking_for("RE2::Match() with endpos argument") do
|
|
174
|
-
test_re2_match_signature = <<SRC
|
|
175
|
-
#include <re2/re2.h>
|
|
176
|
-
|
|
177
|
-
int main() {
|
|
178
|
-
RE2 pattern("test");
|
|
179
|
-
re2::StringPiece *match;
|
|
180
|
-
pattern.Match("test", 0, 0, RE2::UNANCHORED, match, 0);
|
|
181
|
-
|
|
182
|
-
return 0;
|
|
183
|
-
}
|
|
184
|
-
SRC
|
|
185
|
-
|
|
186
|
-
if try_compile(test_re2_match_signature, compile_options)
|
|
187
|
-
$defs.push("-DHAVE_ENDPOS_ARGUMENT")
|
|
188
|
-
end
|
|
189
|
-
end
|
|
103
|
+
def build_with_vendored_libraries
|
|
104
|
+
message "Building re2 using packaged libraries.\n"
|
|
190
105
|
|
|
191
|
-
|
|
192
|
-
test_re2_set_match_signature = <<SRC
|
|
193
|
-
#include <vector>
|
|
194
|
-
#include <re2/re2.h>
|
|
195
|
-
#include <re2/set.h>
|
|
106
|
+
ENV["MACOSX_DEPLOYMENT_TARGET"] = "10.14"
|
|
196
107
|
|
|
197
|
-
|
|
198
|
-
RE2::Set s(RE2::DefaultOptions, RE2::UNANCHORED);
|
|
199
|
-
s.Add("foo", NULL);
|
|
200
|
-
s.Compile();
|
|
108
|
+
abseil_recipe, re2_recipe = load_recipes
|
|
201
109
|
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
110
|
+
process_recipe(abseil_recipe) do |recipe|
|
|
111
|
+
recipe.configure_options << '-DABSL_PROPAGATE_CXX_STD=ON'
|
|
112
|
+
# Workaround for https://github.com/abseil/abseil-cpp/issues/1510
|
|
113
|
+
recipe.configure_options << '-DCMAKE_CXX_FLAGS=-DABSL_FORCE_WAITER_MODE=4 -D_WIN32_WINNT=0x0601' if MiniPortile.windows?
|
|
114
|
+
end
|
|
205
115
|
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
116
|
+
process_recipe(re2_recipe) do |recipe|
|
|
117
|
+
recipe.configure_options += [
|
|
118
|
+
# Specify Abseil's path so RE2 will prefer that over any system Abseil
|
|
119
|
+
"-DCMAKE_PREFIX_PATH=#{abseil_recipe.path}",
|
|
120
|
+
'-DCMAKE_CXX_FLAGS=-DNDEBUG'
|
|
121
|
+
]
|
|
122
|
+
end
|
|
209
123
|
|
|
210
|
-
|
|
211
|
-
|
|
124
|
+
pc_file = File.join(re2_recipe.lib_path, 'pkgconfig', 're2.pc')
|
|
125
|
+
pkg_config_paths = [
|
|
126
|
+
File.join(abseil_recipe.lib_path, 'pkgconfig'),
|
|
127
|
+
File.join(re2_recipe.lib_path, 'pkgconfig')
|
|
128
|
+
]
|
|
129
|
+
|
|
130
|
+
static_pkg_config(pc_file, pkg_config_paths)
|
|
212
131
|
end
|
|
213
|
-
end
|
|
214
|
-
end
|
|
215
132
|
|
|
216
|
-
def
|
|
217
|
-
|
|
218
|
-
|
|
133
|
+
def build_extension
|
|
134
|
+
$CFLAGS << " -Wall -Wextra -funroll-loops"
|
|
135
|
+
$CXXFLAGS << " -Wall -Wextra -funroll-loops"
|
|
219
136
|
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
recipe.target = File.join(recipe.target, target_arch) if cross_build_p
|
|
137
|
+
# Pass -x c++ to force gcc to compile the test program
|
|
138
|
+
# as C++ (as it will end in .c by default).
|
|
139
|
+
compile_options = +"-x c++"
|
|
224
140
|
|
|
225
|
-
|
|
141
|
+
have_library("stdc++")
|
|
226
142
|
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
143
|
+
minimal_program = <<~SRC
|
|
144
|
+
#include <re2/re2.h>
|
|
145
|
+
int main() { return 0; }
|
|
146
|
+
SRC
|
|
230
147
|
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
message(<<~EOM)
|
|
235
|
-
---------- IMPORTANT NOTICE ----------
|
|
236
|
-
Building re2 with a packaged version of #{name}-#{version}.
|
|
237
|
-
Configuration options: #{recipe.configure_options.shelljoin}
|
|
238
|
-
EOM
|
|
148
|
+
re2_requires_version_flag = checking_for("re2 that requires explicit C++ version flag") do
|
|
149
|
+
!try_compile(minimal_program, compile_options)
|
|
150
|
+
end
|
|
239
151
|
|
|
240
|
-
|
|
241
|
-
|
|
152
|
+
if re2_requires_version_flag
|
|
153
|
+
# Recent versions of RE2 depend directly on Abseil, which requires a
|
|
154
|
+
# compiler with C++17 support.
|
|
155
|
+
abort "Cannot compile re2 with your compiler: recent versions require C++17 support." unless %w[c++20 c++17 c++11].any? do |std|
|
|
156
|
+
checking_for("re2 that compiles with #{std} standard") do
|
|
157
|
+
if try_compile(minimal_program, compile_options + " -std=#{std}")
|
|
158
|
+
compile_options << " -std=#{std}"
|
|
159
|
+
$CPPFLAGS << " -std=#{std}"
|
|
160
|
+
|
|
161
|
+
true
|
|
162
|
+
end
|
|
163
|
+
end
|
|
164
|
+
end
|
|
165
|
+
end
|
|
242
166
|
|
|
243
|
-
|
|
244
|
-
|
|
167
|
+
# Determine which version of re2 the user has installed.
|
|
168
|
+
# Revision d9f8806c004d added an `endpos` argument to the
|
|
169
|
+
# generic Match() function.
|
|
170
|
+
#
|
|
171
|
+
# To test for this, try to compile a simple program that uses
|
|
172
|
+
# the newer form of Match() and set a flag if it is successful.
|
|
173
|
+
checking_for("RE2::Match() with endpos argument") do
|
|
174
|
+
test_re2_match_signature = <<~SRC
|
|
175
|
+
#include <re2/re2.h>
|
|
176
|
+
|
|
177
|
+
int main() {
|
|
178
|
+
RE2 pattern("test");
|
|
179
|
+
re2::StringPiece *match;
|
|
180
|
+
pattern.Match("test", 0, 0, RE2::UNANCHORED, match, 0);
|
|
181
|
+
|
|
182
|
+
return 0;
|
|
183
|
+
}
|
|
184
|
+
SRC
|
|
185
|
+
|
|
186
|
+
if try_compile(test_re2_match_signature, compile_options)
|
|
187
|
+
$defs.push("-DHAVE_ENDPOS_ARGUMENT")
|
|
188
|
+
end
|
|
245
189
|
end
|
|
246
|
-
end
|
|
247
190
|
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
191
|
+
checking_for("RE2::Set::Match() with error information") do
|
|
192
|
+
test_re2_set_match_signature = <<~SRC
|
|
193
|
+
#include <vector>
|
|
194
|
+
#include <re2/re2.h>
|
|
195
|
+
#include <re2/set.h>
|
|
251
196
|
|
|
252
|
-
|
|
253
|
-
|
|
197
|
+
int main() {
|
|
198
|
+
RE2::Set s(RE2::DefaultOptions, RE2::UNANCHORED);
|
|
199
|
+
s.Add("foo", NULL);
|
|
200
|
+
s.Compile();
|
|
254
201
|
|
|
255
|
-
|
|
256
|
-
|
|
202
|
+
std::vector<int> v;
|
|
203
|
+
RE2::Set::ErrorInfo ei;
|
|
204
|
+
s.Match("foo", &v, &ei);
|
|
257
205
|
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
"/opt/homebrew/include",
|
|
262
|
-
"/usr/include"
|
|
263
|
-
]
|
|
206
|
+
return 0;
|
|
207
|
+
}
|
|
208
|
+
SRC
|
|
264
209
|
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
]
|
|
210
|
+
if try_compile(test_re2_set_match_signature, compile_options)
|
|
211
|
+
$defs.push("-DHAVE_ERROR_INFO_ARGUMENT")
|
|
212
|
+
end
|
|
213
|
+
end
|
|
270
214
|
|
|
271
|
-
|
|
215
|
+
checking_for("RE2::Set::Size()") do
|
|
216
|
+
test_re2_set_size = <<~SRC
|
|
217
|
+
#include <re2/re2.h>
|
|
218
|
+
#include <re2/set.h>
|
|
272
219
|
|
|
273
|
-
|
|
274
|
-
|
|
220
|
+
int main() {
|
|
221
|
+
RE2::Set s(RE2::DefaultOptions, RE2::UNANCHORED);
|
|
222
|
+
s.Size();
|
|
275
223
|
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
"lib#{Regexp.last_match(1)}.#{$LIBEXT}"
|
|
280
|
-
end
|
|
281
|
-
end
|
|
224
|
+
return 0;
|
|
225
|
+
}
|
|
226
|
+
SRC
|
|
282
227
|
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
# 1. For -L<path> flags, ensure that any `ports` paths are prioritized just
|
|
287
|
-
# in case there are installed libraries that might take precedence.
|
|
288
|
-
# 2. For -l<lib> flags, convert the library to the static library with a
|
|
289
|
-
# full path and substitute the absolute static library. For example,
|
|
290
|
-
# -lre2 maps to /path/to/ports/<arch>/libre2/<version>/lib/libre2.a.
|
|
291
|
-
#
|
|
292
|
-
# This is needed because when building the extension, Ruby appears to
|
|
293
|
-
# insert `-L#{RbConfig::CONFIG['exec_prefix']}/lib` first. If libre2 is
|
|
294
|
-
# in installed in that location then the extension will link against the
|
|
295
|
-
# system library instead of the vendored library.
|
|
296
|
-
def add_flag(arg, lib_paths)
|
|
297
|
-
case arg
|
|
298
|
-
when /\A-L(.+)\z/
|
|
299
|
-
# Prioritize ports' directories
|
|
300
|
-
lib_dir = Regexp.last_match(1)
|
|
301
|
-
$LIBPATH =
|
|
302
|
-
if lib_dir.start_with?(PACKAGE_ROOT_DIR + "/")
|
|
303
|
-
[lib_dir] | $LIBPATH
|
|
304
|
-
else
|
|
305
|
-
$LIBPATH | [lib_dir]
|
|
228
|
+
if try_compile(test_re2_set_size, compile_options)
|
|
229
|
+
$defs.push("-DHAVE_SET_SIZE")
|
|
230
|
+
end
|
|
306
231
|
end
|
|
307
|
-
|
|
308
|
-
filename = libflag_to_filename(arg)
|
|
232
|
+
end
|
|
309
233
|
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
234
|
+
def static_pkg_config(pc_file, pkg_config_paths)
|
|
235
|
+
ENV["PKG_CONFIG_PATH"] = [*pkg_config_paths, ENV["PKG_CONFIG_PATH"]].compact.join(File::PATH_SEPARATOR)
|
|
236
|
+
|
|
237
|
+
static_library_paths = minimal_pkg_config(pc_file, '--libs-only-L', '--static')
|
|
238
|
+
.shellsplit
|
|
239
|
+
.map { |flag| flag.delete_prefix('-L') }
|
|
240
|
+
|
|
241
|
+
# Replace all -l flags that can be found in one of the static library
|
|
242
|
+
# paths with the absolute path instead.
|
|
243
|
+
minimal_pkg_config(pc_file, '--libs-only-l', '--static')
|
|
244
|
+
.shellsplit
|
|
245
|
+
.each do |flag|
|
|
246
|
+
lib = "lib#{flag.delete_prefix('-l')}.#{$LIBEXT}"
|
|
247
|
+
|
|
248
|
+
if (static_lib_path = static_library_paths.find { |path| File.exist?(File.join(path, lib)) })
|
|
249
|
+
$libs << ' ' << File.join(static_lib_path, lib).shellescape
|
|
250
|
+
else
|
|
251
|
+
$libs << ' ' << flag.shellescape
|
|
252
|
+
end
|
|
253
|
+
end
|
|
254
|
+
|
|
255
|
+
append_ldflags(minimal_pkg_config(pc_file, '--libs-only-other', '--static'))
|
|
313
256
|
|
|
314
|
-
|
|
257
|
+
incflags = minimal_pkg_config(pc_file, '--cflags-only-I')
|
|
258
|
+
$INCFLAGS = [incflags, $INCFLAGS].join(" ").strip
|
|
315
259
|
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
260
|
+
cflags = minimal_pkg_config(pc_file, '--cflags-only-other')
|
|
261
|
+
$CFLAGS = [$CFLAGS, cflags].join(" ").strip
|
|
262
|
+
$CXXFLAGS = [$CXXFLAGS, cflags].join(" ").strip
|
|
319
263
|
end
|
|
320
264
|
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
end
|
|
325
|
-
end
|
|
265
|
+
def process_recipe(recipe)
|
|
266
|
+
cross_build_p = config_cross_build?
|
|
267
|
+
message "Cross build is #{cross_build_p ? "enabled" : "disabled"}.\n"
|
|
326
268
|
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
269
|
+
recipe.host = target_host
|
|
270
|
+
# Ensure x64-mingw-ucrt uses different library paths since the host is
|
|
271
|
+
# the same (x86_64-w64-mingw32).
|
|
272
|
+
recipe.target = File.join(recipe.target, target_arch) if cross_build_p
|
|
330
273
|
|
|
331
|
-
|
|
332
|
-
message "Building re2 using packaged libraries.\n"
|
|
274
|
+
yield recipe
|
|
333
275
|
|
|
334
|
-
|
|
276
|
+
checkpoint = "#{recipe.target}/#{recipe.name}-#{recipe.version}-#{recipe.host}.installed"
|
|
277
|
+
name = recipe.name
|
|
278
|
+
version = recipe.version
|
|
335
279
|
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
280
|
+
if File.exist?(checkpoint)
|
|
281
|
+
message("Building re2 with a packaged version of #{name}-#{version}.\n")
|
|
282
|
+
else
|
|
283
|
+
message(<<~EOM)
|
|
284
|
+
---------- IMPORTANT NOTICE ----------
|
|
285
|
+
Building re2 with a packaged version of #{name}-#{version}.
|
|
286
|
+
Configuration options: #{recipe.configure_options.shelljoin}
|
|
287
|
+
EOM
|
|
341
288
|
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
end
|
|
289
|
+
# Use a temporary base directory to reduce filename lengths since
|
|
290
|
+
# Windows can hit a limit of 250 characters (CMAKE_OBJECT_PATH_MAX).
|
|
291
|
+
Dir.mktmpdir { |dir| Dir.chdir(dir) { recipe.cook } }
|
|
346
292
|
|
|
347
|
-
|
|
348
|
-
|
|
293
|
+
FileUtils.touch(checkpoint)
|
|
294
|
+
end
|
|
295
|
+
end
|
|
349
296
|
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
297
|
+
# See MiniPortile2's minimal_pkg_config:
|
|
298
|
+
# https://github.com/flavorjones/mini_portile/blob/52fb0bc41c89a10f1ac7b5abcf0157e059194374/lib/mini_portile2/mini_portile.rb#L760-L783
|
|
299
|
+
# and Ruby's pkg_config:
|
|
300
|
+
# https://github.com/ruby/ruby/blob/c505bb0ca0fd61c7ae931d26451f11122a2644e9/lib/mkmf.rb#L1916-L2004
|
|
301
|
+
def minimal_pkg_config(pc_file, *options)
|
|
302
|
+
if ($PKGCONFIG ||=
|
|
303
|
+
(pkgconfig = MakeMakefile.with_config("pkg-config") {MakeMakefile.config_string("PKG_CONFIG") || "pkg-config"}) &&
|
|
304
|
+
MakeMakefile.find_executable0(pkgconfig) && pkgconfig)
|
|
305
|
+
pkgconfig = $PKGCONFIG
|
|
306
|
+
else
|
|
307
|
+
raise RuntimeError, "pkg-config is not found"
|
|
308
|
+
end
|
|
354
309
|
|
|
355
|
-
|
|
310
|
+
response = xpopen([pkgconfig, *options, pc_file], err: %i[child out], &:read)
|
|
311
|
+
raise RuntimeError, response unless $?.success?
|
|
356
312
|
|
|
357
|
-
|
|
358
|
-
|
|
313
|
+
response.strip
|
|
314
|
+
end
|
|
359
315
|
|
|
360
|
-
|
|
316
|
+
def config_system_libraries?
|
|
317
|
+
enable_config("system-libraries", ENV.key?('RE2_USE_SYSTEM_LIBRARIES'))
|
|
318
|
+
end
|
|
361
319
|
|
|
362
|
-
|
|
363
|
-
|
|
320
|
+
def config_cross_build?
|
|
321
|
+
enable_config("cross-build")
|
|
322
|
+
end
|
|
364
323
|
|
|
365
|
-
|
|
324
|
+
# We use 'host' to set compiler prefix for cross-compiling. Prefer host_alias over host. And
|
|
325
|
+
# prefer i686 (what external dev tools use) to i386 (what ruby's configure.ac emits).
|
|
326
|
+
def target_host
|
|
327
|
+
host = RbConfig::CONFIG["host_alias"].empty? ? RbConfig::CONFIG["host"] : RbConfig::CONFIG["host_alias"]
|
|
328
|
+
host.gsub(/i386/, "i686")
|
|
329
|
+
end
|
|
366
330
|
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
331
|
+
def target_arch
|
|
332
|
+
RbConfig::CONFIG['arch']
|
|
333
|
+
end
|
|
334
|
+
end
|
|
370
335
|
end
|
|
371
336
|
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
337
|
+
extconf = RE2::Extconf.new
|
|
338
|
+
|
|
339
|
+
if arg_config('--help')
|
|
340
|
+
extconf.print_help
|
|
341
|
+
exit!(true)
|
|
376
342
|
end
|
|
377
343
|
|
|
378
|
-
|
|
344
|
+
extconf.configure
|