1 /*
2 * Copyright (c) 2015-2020, Intel Corporation
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are met:
6 *
7 * * Redistributions of source code must retain the above copyright notice,
8 * this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of Intel Corporation nor the names of its contributors
13 * may be used to endorse or promote products derived from this software
14 * without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
20 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26 * POSSIBILITY OF SUCH DAMAGE.
27 */
28
29 #include "nfa_build_util.h"
30
31 #include "limex_internal.h"
32 #include "mcclellancompile.h"
33 #include "mcsheng_compile.h"
34 #include "shengcompile.h"
35 #include "nfa_internal.h"
36 #include "repeat_internal.h"
37 #include "ue2common.h"
38
39 #include <algorithm>
40 #include <cassert>
41 #include <cstddef>
42 #include <cstdio>
43 #include <cstdlib>
44 #include <cstring>
45 #include <sstream>
46
47 using namespace std;
48
49 namespace ue2 {
50
51 namespace {
52
53 template<NFAEngineType t> struct NFATraits { };
54
55 template<template<NFAEngineType t> class sfunc, typename rv_t, typename arg_t,
56 NFAEngineType lb>
57 struct DISPATCH_BY_NFA_TYPE_INT {
doOpue2::__anon648aa2300111::DISPATCH_BY_NFA_TYPE_INT58 static rv_t doOp(NFAEngineType i, const arg_t &arg) {
59 if (i == lb) {
60 return sfunc<lb>::call(arg);
61 } else {
62 return DISPATCH_BY_NFA_TYPE_INT<sfunc, rv_t, arg_t,
63 (NFAEngineType)(lb + 1)>
64 ::doOp(i, arg);
65 }
66 }
67 };
68
69 template<template<NFAEngineType t> class sfunc, typename rv_t, typename arg_t>
70 struct DISPATCH_BY_NFA_TYPE_INT<sfunc, rv_t, arg_t, INVALID_NFA> {
71 // dummy
doOpue2::__anon648aa2300111::DISPATCH_BY_NFA_TYPE_INT72 static rv_t doOp(NFAEngineType, const arg_t &) {
73 assert(0);
74 throw std::logic_error("Unreachable");
75 }
76 };
77
78 #define DISPATCH_BY_NFA_TYPE(i, op, arg) \
79 DISPATCH_BY_NFA_TYPE_INT<op, decltype(op<(NFAEngineType)0>::call(arg)), \
80 decltype(arg), (NFAEngineType)0>::doOp(i, arg)
81 }
82
83 typedef bool (*nfa_dispatch_fn)(const NFA *nfa);
84
85 template<typename T>
86 static
has_accel_limex(const NFA * nfa)87 bool has_accel_limex(const NFA *nfa) {
88 const T *limex = (const T *)getImplNfa(nfa);
89 return limex->accelCount;
90 }
91
92 template<typename T>
93 static
has_repeats_limex(const NFA * nfa)94 bool has_repeats_limex(const NFA *nfa) {
95 const T *limex = (const T *)getImplNfa(nfa);
96 return limex->repeatCount;
97 }
98
99
100 template<typename T>
101 static
has_repeats_other_than_firsts_limex(const NFA * nfa)102 bool has_repeats_other_than_firsts_limex(const NFA *nfa) {
103 const T *limex = (const T *)getImplNfa(nfa);
104 const char *ptr = (const char *)limex;
105
106 const u32 *repeatOffset = (const u32 *)(ptr + limex->repeatOffset);
107
108 for (u32 i = 0; i < limex->repeatCount; i++) {
109 u32 offset = repeatOffset[i];
110 const NFARepeatInfo *info = (const NFARepeatInfo *)(ptr + offset);
111 const RepeatInfo *repeat =
112 (const RepeatInfo *)((const char *)info + sizeof(*info));
113 if (repeat->type != REPEAT_FIRST) {
114 return true;
115 }
116 }
117
118 return false;
119 }
120
121 static
dispatch_false(const NFA *)122 bool dispatch_false(const NFA *) {
123 return false;
124 }
125
126 #ifdef DUMP_SUPPORT
127 namespace {
128 template<NFAEngineType t>
129 struct getName {
callue2::__anon648aa2300211::getName130 static const char *call(void *) {
131 return NFATraits<t>::name;
132 }
133 };
134
135 // descr helper for LimEx NFAs
136 template<NFAEngineType t>
137 static
getDescriptionLimEx(const NFA * nfa)138 string getDescriptionLimEx(const NFA *nfa) {
139 const typename NFATraits<t>::implNFA_t *limex =
140 (const typename NFATraits<t>::implNFA_t *)getImplNfa(nfa);
141 ostringstream oss;
142 oss << NFATraits<t>::name << "/" << limex->exceptionCount;
143 if (limex->repeatCount) {
144 oss << " +" << limex->repeatCount << "r";
145 }
146 return oss.str();
147 }
148 }
149
150 // generic description: just return the name
151 namespace {
152 template<NFAEngineType t>
153 struct getDescription {
callue2::__anon648aa2300311::getDescription154 static string call(const void *) {
155 return string(NFATraits<t>::name);
156 }
157 };
158 }
159 #endif
160
161
162 /* build-utility Traits */
163
164 namespace {
165 enum NFACategory {NFA_LIMEX, NFA_OTHER};
166
167 // Some of our traits we want around in DUMP_SUPPORT mode only.
168 #if defined(DUMP_SUPPORT)
169 #define DO_IF_DUMP_SUPPORT(a) a
170 #else
171 #define DO_IF_DUMP_SUPPORT(a)
172 #endif
173
174 #define MAKE_LIMEX_TRAITS(mlt_size, mlt_align) \
175 template<> struct NFATraits<LIMEX_NFA_##mlt_size> { \
176 static UNUSED const char *name; \
177 static const NFACategory category = NFA_LIMEX; \
178 typedef LimExNFA##mlt_size implNFA_t; \
179 static const nfa_dispatch_fn has_accel; \
180 static const nfa_dispatch_fn has_repeats; \
181 static const nfa_dispatch_fn has_repeats_other_than_firsts; \
182 static const u32 stateAlign = \
183 MAX(mlt_align, alignof(RepeatControl)); \
184 }; \
185 const nfa_dispatch_fn NFATraits<LIMEX_NFA_##mlt_size>::has_accel \
186 = has_accel_limex<LimExNFA##mlt_size>; \
187 const nfa_dispatch_fn NFATraits<LIMEX_NFA_##mlt_size>::has_repeats \
188 = has_repeats_limex<LimExNFA##mlt_size>; \
189 const nfa_dispatch_fn \
190 NFATraits<LIMEX_NFA_##mlt_size>::has_repeats_other_than_firsts \
191 = has_repeats_other_than_firsts_limex<LimExNFA##mlt_size>; \
192 DO_IF_DUMP_SUPPORT( \
193 const char *NFATraits<LIMEX_NFA_##mlt_size>::name \
194 = "LimEx "#mlt_size; \
195 template<> struct getDescription<LIMEX_NFA_##mlt_size> { \
196 static string call(const void *p) { \
197 return getDescriptionLimEx<LIMEX_NFA_##mlt_size>((const NFA *)p); \
198 } \
199 };)
200
201 MAKE_LIMEX_TRAITS(32, alignof(u32))
202 MAKE_LIMEX_TRAITS(64, alignof(m128)) /* special, 32bit arch uses m128 */
203 MAKE_LIMEX_TRAITS(128, alignof(m128))
204 MAKE_LIMEX_TRAITS(256, alignof(m256))
205 MAKE_LIMEX_TRAITS(384, alignof(m384))
206 MAKE_LIMEX_TRAITS(512, alignof(m512))
207
208 template<> struct NFATraits<MCCLELLAN_NFA_8> {
209 UNUSED static const char *name;
210 static const NFACategory category = NFA_OTHER;
211 static const u32 stateAlign = 1;
212 static const nfa_dispatch_fn has_accel;
213 static const nfa_dispatch_fn has_repeats;
214 static const nfa_dispatch_fn has_repeats_other_than_firsts;
215 };
216 const nfa_dispatch_fn NFATraits<MCCLELLAN_NFA_8>::has_accel = has_accel_mcclellan;
217 const nfa_dispatch_fn NFATraits<MCCLELLAN_NFA_8>::has_repeats = dispatch_false;
218 const nfa_dispatch_fn NFATraits<MCCLELLAN_NFA_8>::has_repeats_other_than_firsts = dispatch_false;
219 #if defined(DUMP_SUPPORT)
220 const char *NFATraits<MCCLELLAN_NFA_8>::name = "McClellan 8";
221 #endif
222
223 template<> struct NFATraits<MCCLELLAN_NFA_16> {
224 UNUSED static const char *name;
225 static const NFACategory category = NFA_OTHER;
226 static const u32 stateAlign = 2;
227 static const nfa_dispatch_fn has_accel;
228 static const nfa_dispatch_fn has_repeats;
229 static const nfa_dispatch_fn has_repeats_other_than_firsts;
230 };
231 const nfa_dispatch_fn NFATraits<MCCLELLAN_NFA_16>::has_accel = has_accel_mcclellan;
232 const nfa_dispatch_fn NFATraits<MCCLELLAN_NFA_16>::has_repeats = dispatch_false;
233 const nfa_dispatch_fn NFATraits<MCCLELLAN_NFA_16>::has_repeats_other_than_firsts = dispatch_false;
234 #if defined(DUMP_SUPPORT)
235 const char *NFATraits<MCCLELLAN_NFA_16>::name = "McClellan 16";
236 #endif
237
238 template<> struct NFATraits<GOUGH_NFA_8> {
239 UNUSED static const char *name;
240 static const NFACategory category = NFA_OTHER;
241 static const u32 stateAlign = 8;
242 static const nfa_dispatch_fn has_accel;
243 static const nfa_dispatch_fn has_repeats;
244 static const nfa_dispatch_fn has_repeats_other_than_firsts;
245 };
246 const nfa_dispatch_fn NFATraits<GOUGH_NFA_8>::has_accel = has_accel_mcclellan;
247 const nfa_dispatch_fn NFATraits<GOUGH_NFA_8>::has_repeats = dispatch_false;
248 const nfa_dispatch_fn NFATraits<GOUGH_NFA_8>::has_repeats_other_than_firsts = dispatch_false;
249 #if defined(DUMP_SUPPORT)
250 const char *NFATraits<GOUGH_NFA_8>::name = "Goughfish 8";
251 #endif
252
253 template<> struct NFATraits<GOUGH_NFA_16> {
254 UNUSED static const char *name;
255 static const NFACategory category = NFA_OTHER;
256 static const u32 stateAlign = 8;
257 static const nfa_dispatch_fn has_accel;
258 static const nfa_dispatch_fn has_repeats;
259 static const nfa_dispatch_fn has_repeats_other_than_firsts;
260 };
261 const nfa_dispatch_fn NFATraits<GOUGH_NFA_16>::has_accel = has_accel_mcclellan;
262 const nfa_dispatch_fn NFATraits<GOUGH_NFA_16>::has_repeats = dispatch_false;
263 const nfa_dispatch_fn NFATraits<GOUGH_NFA_16>::has_repeats_other_than_firsts = dispatch_false;
264 #if defined(DUMP_SUPPORT)
265 const char *NFATraits<GOUGH_NFA_16>::name = "Goughfish 16";
266 #endif
267
268 template<> struct NFATraits<MPV_NFA> {
269 UNUSED static const char *name;
270 static const NFACategory category = NFA_OTHER;
271 static const u32 stateAlign = 8;
272 static const nfa_dispatch_fn has_accel;
273 static const nfa_dispatch_fn has_repeats;
274 static const nfa_dispatch_fn has_repeats_other_than_firsts;
275 };
276 const nfa_dispatch_fn NFATraits<MPV_NFA>::has_accel = dispatch_false;
277 const nfa_dispatch_fn NFATraits<MPV_NFA>::has_repeats = dispatch_false;
278 const nfa_dispatch_fn NFATraits<MPV_NFA>::has_repeats_other_than_firsts = dispatch_false;
279 #if defined(DUMP_SUPPORT)
280 const char *NFATraits<MPV_NFA>::name = "Mega-Puff-Vac";
281 #endif
282
283 template<> struct NFATraits<CASTLE_NFA> {
284 UNUSED static const char *name;
285 static const NFACategory category = NFA_OTHER;
286 static const u32 stateAlign = 8;
287 static const nfa_dispatch_fn has_accel;
288 static const nfa_dispatch_fn has_repeats;
289 static const nfa_dispatch_fn has_repeats_other_than_firsts;
290 };
291 const nfa_dispatch_fn NFATraits<CASTLE_NFA>::has_accel = dispatch_false;
292 const nfa_dispatch_fn NFATraits<CASTLE_NFA>::has_repeats = dispatch_false;
293 const nfa_dispatch_fn NFATraits<CASTLE_NFA>::has_repeats_other_than_firsts = dispatch_false;
294 #if defined(DUMP_SUPPORT)
295 const char *NFATraits<CASTLE_NFA>::name = "Castle";
296 #endif
297
298 template<> struct NFATraits<LBR_NFA_DOT> {
299 UNUSED static const char *name;
300 static const NFACategory category = NFA_OTHER;
301 static const u32 stateAlign = 8;
302 static const nfa_dispatch_fn has_accel;
303 static const nfa_dispatch_fn has_repeats;
304 static const nfa_dispatch_fn has_repeats_other_than_firsts;
305 };
306 const nfa_dispatch_fn NFATraits<LBR_NFA_DOT>::has_accel = dispatch_false;
307 const nfa_dispatch_fn NFATraits<LBR_NFA_DOT>::has_repeats = dispatch_false;
308 const nfa_dispatch_fn NFATraits<LBR_NFA_DOT>::has_repeats_other_than_firsts = dispatch_false;
309 #if defined(DUMP_SUPPORT)
310 const char *NFATraits<LBR_NFA_DOT>::name = "Lim Bounded Repeat (D)";
311 #endif
312
313 template<> struct NFATraits<LBR_NFA_VERM> {
314 UNUSED static const char *name;
315 static const NFACategory category = NFA_OTHER;
316 static const u32 stateAlign = 8;
317 static const nfa_dispatch_fn has_accel;
318 static const nfa_dispatch_fn has_repeats;
319 static const nfa_dispatch_fn has_repeats_other_than_firsts;
320 };
321 const nfa_dispatch_fn NFATraits<LBR_NFA_VERM>::has_accel = dispatch_false;
322 const nfa_dispatch_fn NFATraits<LBR_NFA_VERM>::has_repeats = dispatch_false;
323 const nfa_dispatch_fn NFATraits<LBR_NFA_VERM>::has_repeats_other_than_firsts = dispatch_false;
324 #if defined(DUMP_SUPPORT)
325 const char *NFATraits<LBR_NFA_VERM>::name = "Lim Bounded Repeat (V)";
326 #endif
327
328 template<> struct NFATraits<LBR_NFA_NVERM> {
329 UNUSED static const char *name;
330 static const NFACategory category = NFA_OTHER;
331 static const u32 stateAlign = 8;
332 static const nfa_dispatch_fn has_accel;
333 static const nfa_dispatch_fn has_repeats;
334 static const nfa_dispatch_fn has_repeats_other_than_firsts;
335 };
336 const nfa_dispatch_fn NFATraits<LBR_NFA_NVERM>::has_accel = dispatch_false;
337 const nfa_dispatch_fn NFATraits<LBR_NFA_NVERM>::has_repeats = dispatch_false;
338 const nfa_dispatch_fn NFATraits<LBR_NFA_NVERM>::has_repeats_other_than_firsts = dispatch_false;
339 #if defined(DUMP_SUPPORT)
340 const char *NFATraits<LBR_NFA_NVERM>::name = "Lim Bounded Repeat (NV)";
341 #endif
342
343 template<> struct NFATraits<LBR_NFA_SHUF> {
344 UNUSED static const char *name;
345 static const NFACategory category = NFA_OTHER;
346 static const u32 stateAlign = 8;
347 static const nfa_dispatch_fn has_accel;
348 static const nfa_dispatch_fn has_repeats;
349 static const nfa_dispatch_fn has_repeats_other_than_firsts;
350 };
351 const nfa_dispatch_fn NFATraits<LBR_NFA_SHUF>::has_accel = dispatch_false;
352 const nfa_dispatch_fn NFATraits<LBR_NFA_SHUF>::has_repeats = dispatch_false;
353 const nfa_dispatch_fn NFATraits<LBR_NFA_SHUF>::has_repeats_other_than_firsts = dispatch_false;
354 #if defined(DUMP_SUPPORT)
355 const char *NFATraits<LBR_NFA_SHUF>::name = "Lim Bounded Repeat (S)";
356 #endif
357
358 template<> struct NFATraits<LBR_NFA_TRUF> {
359 UNUSED static const char *name;
360 static const NFACategory category = NFA_OTHER;
361 static const u32 stateAlign = 8;
362 static const nfa_dispatch_fn has_accel;
363 static const nfa_dispatch_fn has_repeats;
364 static const nfa_dispatch_fn has_repeats_other_than_firsts;
365 };
366 const nfa_dispatch_fn NFATraits<LBR_NFA_TRUF>::has_accel = dispatch_false;
367 const nfa_dispatch_fn NFATraits<LBR_NFA_TRUF>::has_repeats = dispatch_false;
368 const nfa_dispatch_fn NFATraits<LBR_NFA_TRUF>::has_repeats_other_than_firsts = dispatch_false;
369 #if defined(DUMP_SUPPORT)
370 const char *NFATraits<LBR_NFA_TRUF>::name = "Lim Bounded Repeat (M)";
371 #endif
372
373 template<> struct NFATraits<SHENG_NFA> {
374 UNUSED static const char *name;
375 static const NFACategory category = NFA_OTHER;
376 static const u32 stateAlign = 1;
377 static const nfa_dispatch_fn has_accel;
378 static const nfa_dispatch_fn has_repeats;
379 static const nfa_dispatch_fn has_repeats_other_than_firsts;
380 };
381 const nfa_dispatch_fn NFATraits<SHENG_NFA>::has_accel = has_accel_sheng;
382 const nfa_dispatch_fn NFATraits<SHENG_NFA>::has_repeats = dispatch_false;
383 const nfa_dispatch_fn NFATraits<SHENG_NFA>::has_repeats_other_than_firsts = dispatch_false;
384 #if defined(DUMP_SUPPORT)
385 const char *NFATraits<SHENG_NFA>::name = "Sheng";
386 #endif
387
388 template<> struct NFATraits<TAMARAMA_NFA> {
389 UNUSED static const char *name;
390 static const NFACategory category = NFA_OTHER;
391 static const u32 stateAlign = 64;
392 static const nfa_dispatch_fn has_accel;
393 static const nfa_dispatch_fn has_repeats;
394 static const nfa_dispatch_fn has_repeats_other_than_firsts;
395 };
396 const nfa_dispatch_fn NFATraits<TAMARAMA_NFA>::has_accel = dispatch_false;
397 const nfa_dispatch_fn NFATraits<TAMARAMA_NFA>::has_repeats = dispatch_false;
398 const nfa_dispatch_fn NFATraits<TAMARAMA_NFA>::has_repeats_other_than_firsts = dispatch_false;
399 #if defined(DUMP_SUPPORT)
400 const char *NFATraits<TAMARAMA_NFA>::name = "Tamarama";
401 #endif
402
403 template<> struct NFATraits<MCSHENG_NFA_8> {
404 UNUSED static const char *name;
405 static const NFACategory category = NFA_OTHER;
406 static const u32 stateAlign = 1;
407 static const nfa_dispatch_fn has_accel;
408 static const nfa_dispatch_fn has_repeats;
409 static const nfa_dispatch_fn has_repeats_other_than_firsts;
410 };
411 const nfa_dispatch_fn NFATraits<MCSHENG_NFA_8>::has_accel = has_accel_mcsheng;
412 const nfa_dispatch_fn NFATraits<MCSHENG_NFA_8>::has_repeats = dispatch_false;
413 const nfa_dispatch_fn NFATraits<MCSHENG_NFA_8>::has_repeats_other_than_firsts = dispatch_false;
414 #if defined(DUMP_SUPPORT)
415 const char *NFATraits<MCSHENG_NFA_8>::name = "Shengy McShengFace 8";
416 #endif
417
418 template<> struct NFATraits<MCSHENG_NFA_16> {
419 UNUSED static const char *name;
420 static const NFACategory category = NFA_OTHER;
421 static const u32 stateAlign = 2;
422 static const nfa_dispatch_fn has_accel;
423 static const nfa_dispatch_fn has_repeats;
424 static const nfa_dispatch_fn has_repeats_other_than_firsts;
425 };
426 const nfa_dispatch_fn NFATraits<MCSHENG_NFA_16>::has_accel = has_accel_mcsheng;
427 const nfa_dispatch_fn NFATraits<MCSHENG_NFA_16>::has_repeats = dispatch_false;
428 const nfa_dispatch_fn NFATraits<MCSHENG_NFA_16>::has_repeats_other_than_firsts = dispatch_false;
429 #if defined(DUMP_SUPPORT)
430 const char *NFATraits<MCSHENG_NFA_16>::name = "Shengy McShengFace 16";
431 #endif
432
433 template<> struct NFATraits<SHENG_NFA_32> {
434 UNUSED static const char *name;
435 static const NFACategory category = NFA_OTHER;
436 static const u32 stateAlign = 1;
437 static const nfa_dispatch_fn has_accel;
438 static const nfa_dispatch_fn has_repeats;
439 static const nfa_dispatch_fn has_repeats_other_than_firsts;
440 };
441 const nfa_dispatch_fn NFATraits<SHENG_NFA_32>::has_accel = has_accel_sheng;
442 const nfa_dispatch_fn NFATraits<SHENG_NFA_32>::has_repeats = dispatch_false;
443 const nfa_dispatch_fn NFATraits<SHENG_NFA_32>::has_repeats_other_than_firsts = dispatch_false;
444 #if defined(DUMP_SUPPORT)
445 const char *NFATraits<SHENG_NFA_32>::name = "Sheng 32";
446 #endif
447
448 template<> struct NFATraits<SHENG_NFA_64> {
449 UNUSED static const char *name;
450 static const NFACategory category = NFA_OTHER;
451 static const u32 stateAlign = 1;
452 static const nfa_dispatch_fn has_accel;
453 static const nfa_dispatch_fn has_repeats;
454 static const nfa_dispatch_fn has_repeats_other_than_firsts;
455 };
456 const nfa_dispatch_fn NFATraits<SHENG_NFA_64>::has_accel = has_accel_sheng;
457 const nfa_dispatch_fn NFATraits<SHENG_NFA_64>::has_repeats = dispatch_false;
458 const nfa_dispatch_fn NFATraits<SHENG_NFA_64>::has_repeats_other_than_firsts = dispatch_false;
459 #if defined(DUMP_SUPPORT)
460 const char *NFATraits<SHENG_NFA_64>::name = "Sheng 64";
461 #endif
462
463 template<> struct NFATraits<MCSHENG_64_NFA_8> {
464 UNUSED static const char *name;
465 static const NFACategory category = NFA_OTHER;
466 static const u32 stateAlign = 1;
467 static const nfa_dispatch_fn has_accel;
468 static const nfa_dispatch_fn has_repeats;
469 static const nfa_dispatch_fn has_repeats_other_than_firsts;
470 };
471 const nfa_dispatch_fn NFATraits<MCSHENG_64_NFA_8>::has_accel = has_accel_mcsheng;
472 const nfa_dispatch_fn NFATraits<MCSHENG_64_NFA_8>::has_repeats = dispatch_false;
473 const nfa_dispatch_fn NFATraits<MCSHENG_64_NFA_8>::has_repeats_other_than_firsts = dispatch_false;
474 #if defined(DUMP_SUPPORT)
475 const char *NFATraits<MCSHENG_64_NFA_8>::name = "Shengy64 McShengFace 8";
476 #endif
477
478 template<> struct NFATraits<MCSHENG_64_NFA_16> {
479 UNUSED static const char *name;
480 static const NFACategory category = NFA_OTHER;
481 static const u32 stateAlign = 2;
482 static const nfa_dispatch_fn has_accel;
483 static const nfa_dispatch_fn has_repeats;
484 static const nfa_dispatch_fn has_repeats_other_than_firsts;
485 };
486 const nfa_dispatch_fn NFATraits<MCSHENG_64_NFA_16>::has_accel = has_accel_mcsheng;
487 const nfa_dispatch_fn NFATraits<MCSHENG_64_NFA_16>::has_repeats = dispatch_false;
488 const nfa_dispatch_fn NFATraits<MCSHENG_64_NFA_16>::has_repeats_other_than_firsts = dispatch_false;
489 #if defined(DUMP_SUPPORT)
490 const char *NFATraits<MCSHENG_64_NFA_16>::name = "Shengy64 McShengFace 16";
491 #endif
492 } // namespace
493
494 #if defined(DUMP_SUPPORT)
495
nfa_type_name(NFAEngineType type)496 const char *nfa_type_name(NFAEngineType type) {
497 return DISPATCH_BY_NFA_TYPE(type, getName, nullptr);
498 }
499
describe(const NFA & nfa)500 string describe(const NFA &nfa) {
501 return DISPATCH_BY_NFA_TYPE((NFAEngineType)nfa.type, getDescription, &nfa);
502 }
503
504 #endif /* DUMP_SUPPORT */
505
506 namespace {
507 template<NFAEngineType t>
508 struct getStateAlign {
callue2::__anon648aa2300511::getStateAlign509 static u32 call(void *) {
510 return NFATraits<t>::stateAlign;
511 }
512 };
513 }
514
state_alignment(const NFA & nfa)515 u32 state_alignment(const NFA &nfa) {
516 return DISPATCH_BY_NFA_TYPE((NFAEngineType)nfa.type, getStateAlign, nullptr);
517 }
518
519 namespace {
520 template<NFAEngineType t>
521 struct is_limex {
callue2::__anon648aa2300611::is_limex522 static bool call(const void *) {
523 return NFATraits<t>::category == NFA_LIMEX;
524 }
525 };
526 }
527
528 namespace {
529 template<NFAEngineType t>
530 struct has_repeats_other_than_firsts_dispatch {
callue2::__anon648aa2300711::has_repeats_other_than_firsts_dispatch531 static nfa_dispatch_fn call(const void *) {
532 return NFATraits<t>::has_repeats_other_than_firsts;
533 }
534 };
535 }
536
has_bounded_repeats_other_than_firsts(const NFA & nfa)537 bool has_bounded_repeats_other_than_firsts(const NFA &nfa) {
538 return DISPATCH_BY_NFA_TYPE((NFAEngineType)nfa.type,
539 has_repeats_other_than_firsts_dispatch,
540 &nfa)(&nfa);
541 }
542
543 namespace {
544 template<NFAEngineType t>
545 struct has_repeats_dispatch {
callue2::__anon648aa2300811::has_repeats_dispatch546 static nfa_dispatch_fn call(const void *) {
547 return NFATraits<t>::has_repeats;
548 }
549 };
550 }
551
has_bounded_repeats(const NFA & nfa)552 bool has_bounded_repeats(const NFA &nfa) {
553 return DISPATCH_BY_NFA_TYPE((NFAEngineType)nfa.type, has_repeats_dispatch,
554 &nfa)(&nfa);
555 }
556
557 namespace {
558 template<NFAEngineType t>
559 struct has_accel_dispatch {
callue2::__anon648aa2300911::has_accel_dispatch560 static nfa_dispatch_fn call(const void *) {
561 return NFATraits<t>::has_accel;
562 }
563 };
564 }
565
has_accel(const NFA & nfa)566 bool has_accel(const NFA &nfa) {
567 return DISPATCH_BY_NFA_TYPE((NFAEngineType)nfa.type, has_accel_dispatch,
568 &nfa)(&nfa);
569 }
570
requires_decompress_key(const NFA & nfa)571 bool requires_decompress_key(const NFA &nfa) {
572 return DISPATCH_BY_NFA_TYPE((NFAEngineType)nfa.type, is_limex, &nfa);
573 }
574
575 } // namespace ue2
576