1 /*
2 ** 2000-05-29
3 **
4 ** The author disclaims copyright to this source code. In place of
5 ** a legal notice, here is a blessing:
6 **
7 ** May you do good and not evil.
8 ** May you find forgiveness for yourself and forgive others.
9 ** May you share freely, never taking more than you give.
10 **
11 *************************************************************************
12 ** Driver template for the LEMON parser generator.
13 **
14 ** The "lemon" program processes an LALR(1) input grammar file, then uses
15 ** this template to construct a parser. The "lemon" program inserts text
16 ** at each "%%" line. Also, any "P-a-r-s-e" identifer prefix (without the
17 ** interstitial "-" characters) contained in this template is changed into
18 ** the value of the %name directive from the grammar. Otherwise, the content
19 ** of this template is copied straight through into the generate parser
20 ** source file.
21 **
22 ** The following is the concatenation of all %include directives from the
23 ** input grammar file:
24 */
25 #include <stdio.h>
26 /************ Begin %include sections from the grammar ************************/
27
28
29 #include <stdlib.h>
30 #include <string.h>
31 #include <strings.h>
32 #include <assert.h>
33 #include "parse.h"
34 #include "../util/arr.h"
35 #include "../rmutil/vector.h"
36 #include "../query_node.h"
37
38 // strndup + lowercase in one pass!
strdupcase(const char * s,size_t len)39 char *strdupcase(const char *s, size_t len) {
40 char *ret = rm_strndup(s, len);
41 char *dst = ret;
42 char *src = dst;
43 while (*src) {
44 // unescape
45 if (*src == '\\' && (ispunct(*(src+1)) || isspace(*(src+1)))) {
46 ++src;
47 continue;
48 }
49 *dst = tolower(*src);
50 ++dst;
51 ++src;
52
53 }
54 *dst = '\0';
55
56 return ret;
57 }
58
59 // unescape a string (non null terminated) and return the new length (may be shorter than the original. This manipulates the string itself
unescapen(char * s,size_t sz)60 size_t unescapen(char *s, size_t sz) {
61
62 char *dst = s;
63 char *src = dst;
64 char *end = s + sz;
65 while (src < end) {
66 // unescape
67 if (*src == '\\' && src + 1 < end &&
68 (ispunct(*(src+1)) || isspace(*(src+1)))) {
69 ++src;
70 continue;
71 }
72 *dst++ = *src++;
73 }
74
75 return (size_t)(dst - s);
76 }
77
78 #define NODENN_BOTH_VALID 0
79 #define NODENN_BOTH_INVALID -1
80 #define NODENN_ONE_NULL 1
81 // Returns:
82 // 0 if a && b
83 // -1 if !a && !b
84 // 1 if a ^ b (i.e. !(a&&b||!a||!b)). The result is stored in `out`
one_not_null(void * a,void * b,void * out)85 static int one_not_null(void *a, void *b, void *out) {
86 if (a && b) {
87 return NODENN_BOTH_VALID;
88 } else if (a == NULL && b == NULL) {
89 return NODENN_BOTH_INVALID;
90 } if (a) {
91 *(void **)out = a;
92 return NODENN_ONE_NULL;
93 } else {
94 *(void **)out = b;
95 return NODENN_ONE_NULL;
96 }
97 }
98
99 /**************** End of %include directives **********************************/
100 /* These constants specify the various numeric values for terminal symbols
101 ** in a format understandable to "makeheaders". This section is blank unless
102 ** "lemon" is run with the "-m" command-line option.
103 ***************** Begin makeheaders token definitions *************************/
104 /**************** End makeheaders token definitions ***************************/
105
106 /* The next sections is a series of control #defines.
107 ** various aspects of the generated parser.
108 ** YYCODETYPE is the data type used to store the integer codes
109 ** that represent terminal and non-terminal symbols.
110 ** "unsigned char" is used if there are fewer than
111 ** 256 symbols. Larger types otherwise.
112 ** YYNOCODE is a number of type YYCODETYPE that is not used for
113 ** any terminal or nonterminal symbol.
114 ** YYFALLBACK If defined, this indicates that one or more tokens
115 ** (also known as: "terminal symbols") have fall-back
116 ** values which should be used if the original symbol
117 ** would not parse. This permits keywords to sometimes
118 ** be used as identifiers, for example.
119 ** YYACTIONTYPE is the data type used for "action codes" - numbers
120 ** that indicate what to do in response to the next
121 ** token.
122 ** RSQueryParser_TOKENTYPE is the data type used for minor type for terminal
123 ** symbols. Background: A "minor type" is a semantic
124 ** value associated with a terminal or non-terminal
125 ** symbols. For example, for an "ID" terminal symbol,
126 ** the minor type might be the name of the identifier.
127 ** Each non-terminal can have a different minor type.
128 ** Terminal symbols all have the same minor type, though.
129 ** This macros defines the minor type for terminal
130 ** symbols.
131 ** YYMINORTYPE is the data type used for all minor types.
132 ** This is typically a union of many types, one of
133 ** which is RSQueryParser_TOKENTYPE. The entry in the union
134 ** for terminal symbols is called "yy0".
135 ** YYSTACKDEPTH is the maximum depth of the parser's stack. If
136 ** zero the stack is dynamically sized using realloc()
137 ** RSQueryParser_ARG_SDECL A static variable declaration for the %extra_argument
138 ** RSQueryParser_ARG_PDECL A parameter declaration for the %extra_argument
139 ** RSQueryParser_ARG_PARAM Code to pass %extra_argument as a subroutine parameter
140 ** RSQueryParser_ARG_STORE Code to store %extra_argument into yypParser
141 ** RSQueryParser_ARG_FETCH Code to extract %extra_argument from yypParser
142 ** RSQueryParser_CTX_* As RSQueryParser_ARG_ except for %extra_context
143 ** YYERRORSYMBOL is the code number of the error symbol. If not
144 ** defined, then do no error processing.
145 ** YYNSTATE the combined number of states.
146 ** YYNRULE the number of rules in the grammar
147 ** YYNTOKEN Number of terminal symbols
148 ** YY_MAX_SHIFT Maximum value for shift actions
149 ** YY_MIN_SHIFTREDUCE Minimum value for shift-reduce actions
150 ** YY_MAX_SHIFTREDUCE Maximum value for shift-reduce actions
151 ** YY_ERROR_ACTION The yy_action[] code for syntax error
152 ** YY_ACCEPT_ACTION The yy_action[] code for accept
153 ** YY_NO_ACTION The yy_action[] code for no-op
154 ** YY_MIN_REDUCE Minimum value for reduce actions
155 ** YY_MAX_REDUCE Maximum value for reduce actions
156 */
157 #ifndef INTERFACE
158 # define INTERFACE 1
159 #endif
160 /************* Begin control #defines *****************************************/
161 #define YYCODETYPE unsigned char
162 #define YYNOCODE 42
163 #define YYACTIONTYPE unsigned char
164 #define RSQueryParser_TOKENTYPE QueryToken
165 typedef union {
166 int yyinit;
167 RSQueryParser_TOKENTYPE yy0;
168 QueryNode * yy35;
169 NumericFilter * yy36;
170 QueryAttribute yy55;
171 GeoFilter * yy64;
172 QueryAttribute * yy69;
173 Vector* yy78;
174 RangeNumber yy83;
175 } YYMINORTYPE;
176 #ifndef YYSTACKDEPTH
177 #define YYSTACKDEPTH 100
178 #endif
179 #define RSQueryParser_ARG_SDECL QueryParseCtx *ctx ;
180 #define RSQueryParser_ARG_PDECL , QueryParseCtx *ctx
181 #define RSQueryParser_ARG_PARAM ,ctx
182 #define RSQueryParser_ARG_FETCH QueryParseCtx *ctx =yypParser->ctx ;
183 #define RSQueryParser_ARG_STORE yypParser->ctx =ctx ;
184 #define RSQueryParser_CTX_SDECL
185 #define RSQueryParser_CTX_PDECL
186 #define RSQueryParser_CTX_PARAM
187 #define RSQueryParser_CTX_FETCH
188 #define RSQueryParser_CTX_STORE
189 #define YYNSTATE 62
190 #define YYNRULE 56
191 #define YYNTOKEN 27
192 #define YY_MAX_SHIFT 61
193 #define YY_MIN_SHIFTREDUCE 99
194 #define YY_MAX_SHIFTREDUCE 154
195 #define YY_ERROR_ACTION 155
196 #define YY_ACCEPT_ACTION 156
197 #define YY_NO_ACTION 157
198 #define YY_MIN_REDUCE 158
199 #define YY_MAX_REDUCE 213
200 /************* End control #defines *******************************************/
201
202 /* Define the yytestcase() macro to be a no-op if is not already defined
203 ** otherwise.
204 **
205 ** Applications can choose to define yytestcase() in the %include section
206 ** to a macro that can assist in verifying code coverage. For production
207 ** code the yytestcase() macro should be turned off. But it is useful
208 ** for testing.
209 */
210 #ifndef yytestcase
211 # define yytestcase(X)
212 #endif
213
214
215 /* Next are the tables used to determine what action to take based on the
216 ** current state and lookahead token. These tables are used to implement
217 ** functions that take a state number and lookahead value and return an
218 ** action integer.
219 **
220 ** Suppose the action integer is N. Then the action is determined as
221 ** follows
222 **
223 ** 0 <= N <= YY_MAX_SHIFT Shift N. That is, push the lookahead
224 ** token onto the stack and goto state N.
225 **
226 ** N between YY_MIN_SHIFTREDUCE Shift to an arbitrary state then
227 ** and YY_MAX_SHIFTREDUCE reduce by rule N-YY_MIN_SHIFTREDUCE.
228 **
229 ** N == YY_ERROR_ACTION A syntax error has occurred.
230 **
231 ** N == YY_ACCEPT_ACTION The parser accepts its input.
232 **
233 ** N == YY_NO_ACTION No such action. Denotes unused
234 ** slots in the yy_action[] table.
235 **
236 ** N between YY_MIN_REDUCE Reduce by rule N-YY_MIN_REDUCE
237 ** and YY_MAX_REDUCE
238 **
239 ** The action table is constructed as a single large table named yy_action[].
240 ** Given state S and lookahead X, the action is computed as either:
241 **
242 ** (A) N = yy_action[ yy_shift_ofst[S] + X ]
243 ** (B) N = yy_default[S]
244 **
245 ** The (A) formula is preferred. The B formula is used instead if
246 ** yy_lookahead[yy_shift_ofst[S]+X] is not equal to X.
247 **
248 ** The formulas above are for computing the action when the lookahead is
249 ** a terminal symbol. If the lookahead is a non-terminal (as occurs after
250 ** a reduce action) then the yy_reduce_ofst[] array is used in place of
251 ** the yy_shift_ofst[] array.
252 **
253 ** The following are the tables generated in this section:
254 **
255 ** yy_action[] A single table containing all actions.
256 ** yy_lookahead[] A table containing the lookahead for each entry in
257 ** yy_action. Used to detect hash collisions.
258 ** yy_shift_ofst[] For each state, the offset into yy_action for
259 ** shifting terminals.
260 ** yy_reduce_ofst[] For each state, the offset into yy_action for
261 ** shifting non-terminals after a reduce.
262 ** yy_default[] Default action for each state.
263 **
264 *********** Begin parsing tables **********************************************/
265 #define YY_ACTTAB_COUNT (269)
266 static const YYACTIONTYPE yy_action[] = {
267 /* 0 */ 47, 58, 5, 24, 19, 59, 6, 154, 120, 8,
268 /* 10 */ 153, 126, 23, 32, 7, 108, 133, 158, 9, 5,
269 /* 20 */ 61, 19, 36, 6, 154, 120, 60, 153, 126, 23,
270 /* 30 */ 61, 7, 159, 133, 5, 9, 19, 61, 6, 154,
271 /* 40 */ 120, 153, 153, 126, 23, 211, 7, 181, 133, 25,
272 /* 50 */ 150, 154, 138, 45, 153, 126, 5, 26, 19, 210,
273 /* 60 */ 6, 154, 120, 21, 153, 126, 23, 27, 7, 147,
274 /* 70 */ 133, 160, 154, 142, 56, 153, 126, 17, 180, 28,
275 /* 80 */ 198, 29, 19, 170, 6, 154, 120, 18, 153, 126,
276 /* 90 */ 23, 34, 7, 145, 133, 9, 9, 61, 61, 154,
277 /* 100 */ 154, 50, 153, 153, 40, 31, 114, 13, 193, 1,
278 /* 110 */ 177, 39, 162, 149, 41, 207, 43, 194, 205, 46,
279 /* 120 */ 44, 37, 33, 5, 168, 19, 130, 6, 154, 120,
280 /* 130 */ 131, 153, 126, 23, 49, 7, 38, 133, 132, 154,
281 /* 140 */ 120, 51, 153, 126, 23, 157, 7, 52, 133, 157,
282 /* 150 */ 9, 3, 61, 129, 177, 39, 162, 54, 202, 30,
283 /* 160 */ 43, 169, 42, 156, 44, 37, 55, 14, 128, 35,
284 /* 170 */ 177, 39, 162, 57, 4, 127, 43, 177, 39, 162,
285 /* 180 */ 44, 37, 20, 43, 157, 157, 115, 44, 37, 154,
286 /* 190 */ 123, 11, 153, 157, 177, 39, 162, 157, 2, 157,
287 /* 200 */ 43, 177, 39, 162, 44, 37, 157, 43, 25, 150,
288 /* 210 */ 157, 44, 37, 157, 157, 12, 26, 157, 177, 39,
289 /* 220 */ 162, 157, 15, 157, 43, 177, 39, 162, 44, 37,
290 /* 230 */ 157, 43, 157, 157, 157, 44, 37, 154, 123, 16,
291 /* 240 */ 153, 157, 177, 39, 162, 157, 154, 53, 43, 153,
292 /* 250 */ 157, 157, 44, 37, 157, 157, 154, 48, 157, 153,
293 /* 260 */ 157, 22, 116, 157, 157, 154, 157, 157, 153,
294 };
295 static const YYCODETYPE yy_lookahead[] = {
296 /* 0 */ 37, 41, 2, 31, 4, 41, 6, 7, 8, 5,
297 /* 10 */ 10, 11, 12, 41, 14, 15, 16, 0, 18, 2,
298 /* 20 */ 20, 4, 18, 6, 7, 8, 13, 10, 11, 12,
299 /* 30 */ 20, 14, 0, 16, 2, 18, 4, 20, 6, 7,
300 /* 40 */ 8, 10, 10, 11, 12, 37, 14, 41, 16, 6,
301 /* 50 */ 7, 7, 8, 21, 10, 11, 2, 14, 4, 37,
302 /* 60 */ 6, 7, 8, 37, 10, 11, 12, 37, 14, 26,
303 /* 70 */ 16, 0, 7, 8, 41, 10, 11, 23, 41, 25,
304 /* 80 */ 30, 31, 4, 28, 6, 7, 8, 18, 10, 11,
305 /* 90 */ 12, 41, 14, 24, 16, 18, 18, 20, 20, 7,
306 /* 100 */ 7, 8, 10, 10, 22, 12, 24, 27, 41, 5,
307 /* 110 */ 30, 31, 32, 26, 34, 35, 36, 41, 38, 10,
308 /* 120 */ 40, 41, 18, 2, 41, 4, 12, 6, 7, 8,
309 /* 130 */ 12, 10, 11, 12, 12, 14, 5, 16, 12, 7,
310 /* 140 */ 8, 12, 10, 11, 12, 42, 14, 12, 16, 42,
311 /* 150 */ 18, 27, 20, 12, 30, 31, 32, 12, 30, 31,
312 /* 160 */ 36, 28, 29, 39, 40, 41, 12, 27, 12, 41,
313 /* 170 */ 30, 31, 32, 12, 27, 12, 36, 30, 31, 32,
314 /* 180 */ 40, 41, 23, 36, 42, 42, 4, 40, 41, 7,
315 /* 190 */ 8, 27, 10, 42, 30, 31, 32, 42, 27, 42,
316 /* 200 */ 36, 30, 31, 32, 40, 41, 42, 36, 6, 7,
317 /* 210 */ 42, 40, 41, 42, 42, 27, 14, 42, 30, 31,
318 /* 220 */ 32, 42, 27, 42, 36, 30, 31, 32, 40, 41,
319 /* 230 */ 42, 36, 42, 42, 42, 40, 41, 7, 8, 27,
320 /* 240 */ 10, 42, 30, 31, 32, 42, 7, 8, 36, 10,
321 /* 250 */ 42, 42, 40, 41, 42, 42, 7, 8, 42, 10,
322 /* 260 */ 42, 12, 4, 42, 42, 7, 42, 42, 10, 42,
323 /* 270 */ 42, 42, 42, 42, 42, 42, 42, 42, 42, 42,
324 /* 280 */ 42, 42, 42, 42, 42, 42, 42, 42, 42, 42,
325 };
326 #define YY_SHIFT_COUNT (61)
327 #define YY_SHIFT_MIN (0)
328 #define YY_SHIFT_MAX (258)
329 static const unsigned short int yy_shift_ofst[] = {
330 /* 0 */ 32, 54, 0, 17, 78, 121, 121, 121, 121, 121,
331 /* 10 */ 121, 132, 77, 77, 77, 10, 10, 44, 65, 92,
332 /* 20 */ 13, 43, 93, 249, 182, 202, 202, 202, 202, 230,
333 /* 30 */ 230, 239, 258, 92, 92, 92, 92, 92, 92, 31,
334 /* 40 */ 13, 69, 82, 4, 104, 71, 87, 109, 114, 118,
335 /* 50 */ 122, 126, 129, 135, 141, 145, 154, 156, 161, 163,
336 /* 60 */ 131, 159,
337 };
338 #define YY_REDUCE_COUNT (40)
339 #define YY_REDUCE_MIN (-40)
340 #define YY_REDUCE_MAX (212)
341 static const short yy_reduce_ofst[] = {
342 /* 0 */ 124, 80, 140, 140, 140, 147, 164, 171, 188, 195,
343 /* 10 */ 212, 140, 140, 140, 140, 140, 140, 50, 128, -28,
344 /* 20 */ 133, -37, -40, -36, 6, 8, 22, 26, 30, 6,
345 /* 30 */ 6, 33, 37, 67, 37, 37, 76, 37, 83, 6,
346 /* 40 */ 55,
347 };
348 static const YYACTIONTYPE yy_default[] = {
349 /* 0 */ 155, 155, 155, 155, 184, 155, 155, 155, 155, 155,
350 /* 10 */ 155, 183, 166, 165, 161, 163, 164, 155, 155, 155,
351 /* 20 */ 172, 155, 155, 155, 155, 155, 155, 155, 155, 199,
352 /* 30 */ 203, 155, 155, 155, 196, 200, 155, 176, 155, 178,
353 /* 40 */ 171, 195, 155, 155, 155, 155, 155, 155, 155, 155,
354 /* 50 */ 155, 155, 155, 155, 155, 155, 155, 155, 155, 155,
355 /* 60 */ 155, 155,
356 };
357 /********** End of lemon-generated parsing tables *****************************/
358
359 /* The next table maps tokens (terminal symbols) into fallback tokens.
360 ** If a construct like the following:
361 **
362 ** %fallback ID X Y Z.
363 **
364 ** appears in the grammar, then ID becomes a fallback token for X, Y,
365 ** and Z. Whenever one of the tokens X, Y, or Z is input to the parser
366 ** but it does not parse, the type of the token is changed to ID and
367 ** the parse is retried before an error is thrown.
368 **
369 ** This feature can be used, for example, to cause some keywords in a language
370 ** to revert to identifiers if they keyword does not apply in the context where
371 ** it appears.
372 */
373 #ifdef YYFALLBACK
374 static const YYCODETYPE yyFallback[] = {
375 };
376 #endif /* YYFALLBACK */
377
378 /* The following structure represents a single element of the
379 ** parser's stack. Information stored includes:
380 **
381 ** + The state number for the parser at this level of the stack.
382 **
383 ** + The value of the token stored at this level of the stack.
384 ** (In other words, the "major" token.)
385 **
386 ** + The semantic value stored at this level of the stack. This is
387 ** the information used by the action routines in the grammar.
388 ** It is sometimes called the "minor" token.
389 **
390 ** After the "shift" half of a SHIFTREDUCE action, the stateno field
391 ** actually contains the reduce action for the second half of the
392 ** SHIFTREDUCE.
393 */
394 struct yyStackEntry {
395 YYACTIONTYPE stateno; /* The state-number, or reduce action in SHIFTREDUCE */
396 YYCODETYPE major; /* The major token value. This is the code
397 ** number for the token at this stack level */
398 YYMINORTYPE minor; /* The user-supplied minor token value. This
399 ** is the value of the token */
400 };
401 typedef struct yyStackEntry yyStackEntry;
402
403 /* The state of the parser is completely contained in an instance of
404 ** the following structure */
405 struct yyParser {
406 yyStackEntry *yytos; /* Pointer to top element of the stack */
407 #ifdef YYTRACKMAXSTACKDEPTH
408 int yyhwm; /* High-water mark of the stack */
409 #endif
410 #ifndef YYNOERRORRECOVERY
411 int yyerrcnt; /* Shifts left before out of the error */
412 #endif
413 RSQueryParser_ARG_SDECL /* A place to hold %extra_argument */
414 RSQueryParser_CTX_SDECL /* A place to hold %extra_context */
415 #if YYSTACKDEPTH<=0
416 int yystksz; /* Current side of the stack */
417 yyStackEntry *yystack; /* The parser's stack */
418 yyStackEntry yystk0; /* First stack entry */
419 #else
420 yyStackEntry yystack[YYSTACKDEPTH]; /* The parser's stack */
421 yyStackEntry *yystackEnd; /* Last entry in the stack */
422 #endif
423 };
424 typedef struct yyParser yyParser;
425
426 #ifndef NDEBUG
427 #include <stdio.h>
428 static FILE *yyTraceFILE = 0;
429 static char *yyTracePrompt = 0;
430 #endif /* NDEBUG */
431
432 #ifndef NDEBUG
433 /*
434 ** Turn parser tracing on by giving a stream to which to write the trace
435 ** and a prompt to preface each trace message. Tracing is turned off
436 ** by making either argument NULL
437 **
438 ** Inputs:
439 ** <ul>
440 ** <li> A FILE* to which trace output should be written.
441 ** If NULL, then tracing is turned off.
442 ** <li> A prefix string written at the beginning of every
443 ** line of trace output. If NULL, then tracing is
444 ** turned off.
445 ** </ul>
446 **
447 ** Outputs:
448 ** None.
449 */
RSQueryParser_Trace(FILE * TraceFILE,char * zTracePrompt)450 void RSQueryParser_Trace(FILE *TraceFILE, char *zTracePrompt){
451 yyTraceFILE = TraceFILE;
452 yyTracePrompt = zTracePrompt;
453 if( yyTraceFILE==0 ) yyTracePrompt = 0;
454 else if( yyTracePrompt==0 ) yyTraceFILE = 0;
455 }
456 #endif /* NDEBUG */
457
458 #if defined(YYCOVERAGE) || !defined(NDEBUG)
459 /* For tracing shifts, the names of all terminals and nonterminals
460 ** are required. The following table supplies these names */
461 static const char *const yyTokenName[] = {
462 /* 0 */ "$",
463 /* 1 */ "LOWEST",
464 /* 2 */ "TILDE",
465 /* 3 */ "TAGLIST",
466 /* 4 */ "QUOTE",
467 /* 5 */ "COLON",
468 /* 6 */ "MINUS",
469 /* 7 */ "NUMBER",
470 /* 8 */ "STOPWORD",
471 /* 9 */ "TERMLIST",
472 /* 10 */ "TERM",
473 /* 11 */ "PREFIX",
474 /* 12 */ "PERCENT",
475 /* 13 */ "ATTRIBUTE",
476 /* 14 */ "LP",
477 /* 15 */ "RP",
478 /* 16 */ "MODIFIER",
479 /* 17 */ "AND",
480 /* 18 */ "OR",
481 /* 19 */ "ORX",
482 /* 20 */ "ARROW",
483 /* 21 */ "STAR",
484 /* 22 */ "SEMICOLON",
485 /* 23 */ "LB",
486 /* 24 */ "RB",
487 /* 25 */ "LSQB",
488 /* 26 */ "RSQB",
489 /* 27 */ "expr",
490 /* 28 */ "attribute",
491 /* 29 */ "attribute_list",
492 /* 30 */ "prefix",
493 /* 31 */ "termlist",
494 /* 32 */ "union",
495 /* 33 */ "fuzzy",
496 /* 34 */ "tag_list",
497 /* 35 */ "geo_filter",
498 /* 36 */ "modifierlist",
499 /* 37 */ "num",
500 /* 38 */ "numeric_range",
501 /* 39 */ "query",
502 /* 40 */ "modifier",
503 /* 41 */ "term",
504 };
505 #endif /* defined(YYCOVERAGE) || !defined(NDEBUG) */
506
507 #ifndef NDEBUG
508 /* For tracing reduce actions, the names of all rules are required.
509 */
510 static const char *const yyRuleName[] = {
511 /* 0 */ "query ::= expr",
512 /* 1 */ "query ::=",
513 /* 2 */ "query ::= STAR",
514 /* 3 */ "expr ::= expr expr",
515 /* 4 */ "expr ::= union",
516 /* 5 */ "union ::= expr OR expr",
517 /* 6 */ "union ::= union OR expr",
518 /* 7 */ "expr ::= modifier COLON expr",
519 /* 8 */ "expr ::= modifierlist COLON expr",
520 /* 9 */ "expr ::= LP expr RP",
521 /* 10 */ "attribute ::= ATTRIBUTE COLON term",
522 /* 11 */ "attribute_list ::= attribute",
523 /* 12 */ "attribute_list ::= attribute_list SEMICOLON attribute",
524 /* 13 */ "attribute_list ::= attribute_list SEMICOLON",
525 /* 14 */ "attribute_list ::=",
526 /* 15 */ "expr ::= expr ARROW LB attribute_list RB",
527 /* 16 */ "expr ::= QUOTE termlist QUOTE",
528 /* 17 */ "expr ::= QUOTE term QUOTE",
529 /* 18 */ "expr ::= term",
530 /* 19 */ "expr ::= prefix",
531 /* 20 */ "expr ::= termlist",
532 /* 21 */ "expr ::= STOPWORD",
533 /* 22 */ "termlist ::= term term",
534 /* 23 */ "termlist ::= termlist term",
535 /* 24 */ "termlist ::= termlist STOPWORD",
536 /* 25 */ "expr ::= MINUS expr",
537 /* 26 */ "expr ::= TILDE expr",
538 /* 27 */ "prefix ::= PREFIX",
539 /* 28 */ "expr ::= PERCENT term PERCENT",
540 /* 29 */ "expr ::= PERCENT PERCENT term PERCENT PERCENT",
541 /* 30 */ "expr ::= PERCENT PERCENT PERCENT term PERCENT PERCENT PERCENT",
542 /* 31 */ "expr ::= PERCENT STOPWORD PERCENT",
543 /* 32 */ "expr ::= PERCENT PERCENT STOPWORD PERCENT PERCENT",
544 /* 33 */ "expr ::= PERCENT PERCENT PERCENT STOPWORD PERCENT PERCENT PERCENT",
545 /* 34 */ "modifier ::= MODIFIER",
546 /* 35 */ "modifierlist ::= modifier OR term",
547 /* 36 */ "modifierlist ::= modifierlist OR term",
548 /* 37 */ "expr ::= modifier COLON tag_list",
549 /* 38 */ "tag_list ::= LB term",
550 /* 39 */ "tag_list ::= LB STOPWORD",
551 /* 40 */ "tag_list ::= LB prefix",
552 /* 41 */ "tag_list ::= LB termlist",
553 /* 42 */ "tag_list ::= tag_list OR term",
554 /* 43 */ "tag_list ::= tag_list OR STOPWORD",
555 /* 44 */ "tag_list ::= tag_list OR prefix",
556 /* 45 */ "tag_list ::= tag_list OR termlist",
557 /* 46 */ "tag_list ::= tag_list RB",
558 /* 47 */ "expr ::= modifier COLON numeric_range",
559 /* 48 */ "numeric_range ::= LSQB num num RSQB",
560 /* 49 */ "expr ::= modifier COLON geo_filter",
561 /* 50 */ "geo_filter ::= LSQB num num num TERM RSQB",
562 /* 51 */ "num ::= NUMBER",
563 /* 52 */ "num ::= LP num",
564 /* 53 */ "num ::= MINUS num",
565 /* 54 */ "term ::= TERM",
566 /* 55 */ "term ::= NUMBER",
567 };
568 #endif /* NDEBUG */
569
570
571 #if YYSTACKDEPTH<=0
572 /*
573 ** Try to increase the size of the parser stack. Return the number
574 ** of errors. Return 0 on success.
575 */
yyGrowStack(yyParser * p)576 static int yyGrowStack(yyParser *p){
577 int newSize;
578 int idx;
579 yyStackEntry *pNew;
580
581 newSize = p->yystksz*2 + 100;
582 idx = p->yytos ? (int)(p->yytos - p->yystack) : 0;
583 if( p->yystack==&p->yystk0 ){
584 pNew = malloc(newSize*sizeof(pNew[0]));
585 if( pNew ) pNew[0] = p->yystk0;
586 }else{
587 pNew = realloc(p->yystack, newSize*sizeof(pNew[0]));
588 }
589 if( pNew ){
590 p->yystack = pNew;
591 p->yytos = &p->yystack[idx];
592 #ifndef NDEBUG
593 if( yyTraceFILE ){
594 fprintf(yyTraceFILE,"%sStack grows from %d to %d entries.\n",
595 yyTracePrompt, p->yystksz, newSize);
596 }
597 #endif
598 p->yystksz = newSize;
599 }
600 return pNew==0;
601 }
602 #endif
603
604 /* Datatype of the argument to the memory allocated passed as the
605 ** second argument to RSQueryParser_Alloc() below. This can be changed by
606 ** putting an appropriate #define in the %include section of the input
607 ** grammar.
608 */
609 #ifndef YYMALLOCARGTYPE
610 # define YYMALLOCARGTYPE size_t
611 #endif
612
613 /* Initialize a new parser that has already been allocated.
614 */
RSQueryParser_Init(void * yypRawParser RSQueryParser_CTX_PDECL)615 void RSQueryParser_Init(void *yypRawParser RSQueryParser_CTX_PDECL){
616 yyParser *yypParser = (yyParser*)yypRawParser;
617 RSQueryParser_CTX_STORE
618 #ifdef YYTRACKMAXSTACKDEPTH
619 yypParser->yyhwm = 0;
620 #endif
621 #if YYSTACKDEPTH<=0
622 yypParser->yytos = NULL;
623 yypParser->yystack = NULL;
624 yypParser->yystksz = 0;
625 if( yyGrowStack(yypParser) ){
626 yypParser->yystack = &yypParser->yystk0;
627 yypParser->yystksz = 1;
628 }
629 #endif
630 #ifndef YYNOERRORRECOVERY
631 yypParser->yyerrcnt = -1;
632 #endif
633 yypParser->yytos = yypParser->yystack;
634 yypParser->yystack[0].stateno = 0;
635 yypParser->yystack[0].major = 0;
636 #if YYSTACKDEPTH>0
637 yypParser->yystackEnd = &yypParser->yystack[YYSTACKDEPTH-1];
638 #endif
639 }
640
641 #ifndef RSQueryParser__ENGINEALWAYSONSTACK
642 /*
643 ** This function allocates a new parser.
644 ** The only argument is a pointer to a function which works like
645 ** malloc.
646 **
647 ** Inputs:
648 ** A pointer to the function used to allocate memory.
649 **
650 ** Outputs:
651 ** A pointer to a parser. This pointer is used in subsequent calls
652 ** to RSQueryParser_ and RSQueryParser_Free.
653 */
RSQueryParser_Alloc(void * (* mallocProc)(YYMALLOCARGTYPE)RSQueryParser_CTX_PDECL)654 void *RSQueryParser_Alloc(void *(*mallocProc)(YYMALLOCARGTYPE) RSQueryParser_CTX_PDECL){
655 yyParser *yypParser;
656 yypParser = (yyParser*)(*mallocProc)( (YYMALLOCARGTYPE)sizeof(yyParser) );
657 if( yypParser ){
658 RSQueryParser_CTX_STORE
659 RSQueryParser_Init(yypParser RSQueryParser_CTX_PARAM);
660 }
661 return (void*)yypParser;
662 }
663 #endif /* RSQueryParser__ENGINEALWAYSONSTACK */
664
665
666 /* The following function deletes the "minor type" or semantic value
667 ** associated with a symbol. The symbol can be either a terminal
668 ** or nonterminal. "yymajor" is the symbol code, and "yypminor" is
669 ** a pointer to the value to be deleted. The code used to do the
670 ** deletions is derived from the %destructor and/or %token_destructor
671 ** directives of the input grammar.
672 */
yy_destructor(yyParser * yypParser,YYCODETYPE yymajor,YYMINORTYPE * yypminor)673 static void yy_destructor(
674 yyParser *yypParser, /* The parser */
675 YYCODETYPE yymajor, /* Type code for object to destroy */
676 YYMINORTYPE *yypminor /* The object to be destroyed */
677 ){
678 RSQueryParser_ARG_FETCH
679 RSQueryParser_CTX_FETCH
680 switch( yymajor ){
681 /* Here is inserted the actions which take place when a
682 ** terminal or non-terminal is destroyed. This can happen
683 ** when the symbol is popped from the stack during a
684 ** reduce or during error processing or when a parser is
685 ** being destroyed before it is finished parsing.
686 **
687 ** Note: during a reduce, the only symbols destroyed are those
688 ** which appear on the RHS of the rule, but which are *not* used
689 ** inside the C code.
690 */
691 /********* Begin destructor definitions ***************************************/
692 /* Default NON-TERMINAL Destructor */
693 case 37: /* num */
694 case 39: /* query */
695 case 40: /* modifier */
696 case 41: /* term */
697 {
698
699 }
700 break;
701 case 27: /* expr */
702 case 30: /* prefix */
703 case 31: /* termlist */
704 case 32: /* union */
705 case 33: /* fuzzy */
706 case 34: /* tag_list */
707 {
708 QueryNode_Free((yypminor->yy35));
709 }
710 break;
711 case 28: /* attribute */
712 {
713 rm_free((char*)(yypminor->yy55).value);
714 }
715 break;
716 case 29: /* attribute_list */
717 {
718 array_free_ex((yypminor->yy69), rm_free((char*)((QueryAttribute*)ptr )->value));
719 }
720 break;
721 case 35: /* geo_filter */
722 {
723 GeoFilter_Free((yypminor->yy64));
724 }
725 break;
726 case 36: /* modifierlist */
727 {
728
729 for (size_t i = 0; i < Vector_Size((yypminor->yy78)); i++) {
730 char *s;
731 Vector_Get((yypminor->yy78), i, &s);
732 rm_free(s);
733 }
734 Vector_Free((yypminor->yy78));
735
736 }
737 break;
738 case 38: /* numeric_range */
739 {
740
741 NumericFilter_Free((yypminor->yy36));
742
743 }
744 break;
745 /********* End destructor definitions *****************************************/
746 default: break; /* If no destructor action specified: do nothing */
747 }
748 }
749
750 /*
751 ** Pop the parser's stack once.
752 **
753 ** If there is a destructor routine associated with the token which
754 ** is popped from the stack, then call it.
755 */
yy_pop_parser_stack(yyParser * pParser)756 static void yy_pop_parser_stack(yyParser *pParser){
757 yyStackEntry *yytos;
758 assert( pParser->yytos!=0 );
759 assert( pParser->yytos > pParser->yystack );
760 yytos = pParser->yytos--;
761 #ifndef NDEBUG
762 if( yyTraceFILE ){
763 fprintf(yyTraceFILE,"%sPopping %s\n",
764 yyTracePrompt,
765 yyTokenName[yytos->major]);
766 }
767 #endif
768 yy_destructor(pParser, yytos->major, &yytos->minor);
769 }
770
771 /*
772 ** Clear all secondary memory allocations from the parser
773 */
RSQueryParser_Finalize(void * p)774 void RSQueryParser_Finalize(void *p){
775 yyParser *pParser = (yyParser*)p;
776 while( pParser->yytos>pParser->yystack ) yy_pop_parser_stack(pParser);
777 #if YYSTACKDEPTH<=0
778 if( pParser->yystack!=&pParser->yystk0 ) free(pParser->yystack);
779 #endif
780 }
781
782 #ifndef RSQueryParser__ENGINEALWAYSONSTACK
783 /*
784 ** Deallocate and destroy a parser. Destructors are called for
785 ** all stack elements before shutting the parser down.
786 **
787 ** If the YYPARSEFREENEVERNULL macro exists (for example because it
788 ** is defined in a %include section of the input grammar) then it is
789 ** assumed that the input pointer is never NULL.
790 */
RSQueryParser_Free(void * p,void (* freeProc)(void *))791 void RSQueryParser_Free(
792 void *p, /* The parser to be deleted */
793 void (*freeProc)(void*) /* Function used to reclaim memory */
794 ){
795 #ifndef YYPARSEFREENEVERNULL
796 if( p==0 ) return;
797 #endif
798 RSQueryParser_Finalize(p);
799 (*freeProc)(p);
800 }
801 #endif /* RSQueryParser__ENGINEALWAYSONSTACK */
802
803 /*
804 ** Return the peak depth of the stack for a parser.
805 */
806 #ifdef YYTRACKMAXSTACKDEPTH
RSQueryParser_StackPeak(void * p)807 int RSQueryParser_StackPeak(void *p){
808 yyParser *pParser = (yyParser*)p;
809 return pParser->yyhwm;
810 }
811 #endif
812
813 /* This array of booleans keeps track of the parser statement
814 ** coverage. The element yycoverage[X][Y] is set when the parser
815 ** is in state X and has a lookahead token Y. In a well-tested
816 ** systems, every element of this matrix should end up being set.
817 */
818 #if defined(YYCOVERAGE)
819 static unsigned char yycoverage[YYNSTATE][YYNTOKEN];
820 #endif
821
822 /*
823 ** Write into out a description of every state/lookahead combination that
824 **
825 ** (1) has not been used by the parser, and
826 ** (2) is not a syntax error.
827 **
828 ** Return the number of missed state/lookahead combinations.
829 */
830 #if defined(YYCOVERAGE)
RSQueryParser_Coverage(FILE * out)831 int RSQueryParser_Coverage(FILE *out){
832 int stateno, iLookAhead, i;
833 int nMissed = 0;
834 for(stateno=0; stateno<YYNSTATE; stateno++){
835 i = yy_shift_ofst[stateno];
836 for(iLookAhead=0; iLookAhead<YYNTOKEN; iLookAhead++){
837 if( yy_lookahead[i+iLookAhead]!=iLookAhead ) continue;
838 if( yycoverage[stateno][iLookAhead]==0 ) nMissed++;
839 if( out ){
840 fprintf(out,"State %d lookahead %s %s\n", stateno,
841 yyTokenName[iLookAhead],
842 yycoverage[stateno][iLookAhead] ? "ok" : "missed");
843 }
844 }
845 }
846 return nMissed;
847 }
848 #endif
849
850 /*
851 ** Find the appropriate action for a parser given the terminal
852 ** look-ahead token iLookAhead.
853 */
yy_find_shift_action(YYCODETYPE iLookAhead,YYACTIONTYPE stateno)854 static YYACTIONTYPE yy_find_shift_action(
855 YYCODETYPE iLookAhead, /* The look-ahead token */
856 YYACTIONTYPE stateno /* Current state number */
857 ){
858 int i;
859
860 if( stateno>YY_MAX_SHIFT ) return stateno;
861 assert( stateno <= YY_SHIFT_COUNT );
862 #if defined(YYCOVERAGE)
863 yycoverage[stateno][iLookAhead] = 1;
864 #endif
865 do{
866 i = yy_shift_ofst[stateno];
867 assert( i>=0 );
868 assert( i+YYNTOKEN<=(int)sizeof(yy_lookahead)/sizeof(yy_lookahead[0]) );
869 assert( iLookAhead!=YYNOCODE );
870 assert( iLookAhead < YYNTOKEN );
871 i += iLookAhead;
872 if( yy_lookahead[i]!=iLookAhead ){
873 #ifdef YYFALLBACK
874 YYCODETYPE iFallback; /* Fallback token */
875 if( iLookAhead<sizeof(yyFallback)/sizeof(yyFallback[0])
876 && (iFallback = yyFallback[iLookAhead])!=0 ){
877 #ifndef NDEBUG
878 if( yyTraceFILE ){
879 fprintf(yyTraceFILE, "%sFALLBACK %s => %s\n",
880 yyTracePrompt, yyTokenName[iLookAhead], yyTokenName[iFallback]);
881 }
882 #endif
883 assert( yyFallback[iFallback]==0 ); /* Fallback loop must terminate */
884 iLookAhead = iFallback;
885 continue;
886 }
887 #endif
888 #ifdef YYWILDCARD
889 {
890 int j = i - iLookAhead + YYWILDCARD;
891 if(
892 #if YY_SHIFT_MIN+YYWILDCARD<0
893 j>=0 &&
894 #endif
895 #if YY_SHIFT_MAX+YYWILDCARD>=YY_ACTTAB_COUNT
896 j<YY_ACTTAB_COUNT &&
897 #endif
898 yy_lookahead[j]==YYWILDCARD && iLookAhead>0
899 ){
900 #ifndef NDEBUG
901 if( yyTraceFILE ){
902 fprintf(yyTraceFILE, "%sWILDCARD %s => %s\n",
903 yyTracePrompt, yyTokenName[iLookAhead],
904 yyTokenName[YYWILDCARD]);
905 }
906 #endif /* NDEBUG */
907 return yy_action[j];
908 }
909 }
910 #endif /* YYWILDCARD */
911 return yy_default[stateno];
912 }else{
913 return yy_action[i];
914 }
915 }while(1);
916 }
917
918 /*
919 ** Find the appropriate action for a parser given the non-terminal
920 ** look-ahead token iLookAhead.
921 */
yy_find_reduce_action(YYACTIONTYPE stateno,YYCODETYPE iLookAhead)922 static int yy_find_reduce_action(
923 YYACTIONTYPE stateno, /* Current state number */
924 YYCODETYPE iLookAhead /* The look-ahead token */
925 ){
926 int i;
927 #ifdef YYERRORSYMBOL
928 if( stateno>YY_REDUCE_COUNT ){
929 return yy_default[stateno];
930 }
931 #else
932 assert( stateno<=YY_REDUCE_COUNT );
933 #endif
934 i = yy_reduce_ofst[stateno];
935 assert( iLookAhead!=YYNOCODE );
936 i += iLookAhead;
937 #ifdef YYERRORSYMBOL
938 if( i<0 || i>=YY_ACTTAB_COUNT || yy_lookahead[i]!=iLookAhead ){
939 return yy_default[stateno];
940 }
941 #else
942 assert( i>=0 && i<YY_ACTTAB_COUNT );
943 assert( yy_lookahead[i]==iLookAhead );
944 #endif
945 return yy_action[i];
946 }
947
948 /*
949 ** The following routine is called if the stack overflows.
950 */
yyStackOverflow(yyParser * yypParser)951 static void yyStackOverflow(yyParser *yypParser){
952 RSQueryParser_ARG_FETCH
953 RSQueryParser_CTX_FETCH
954 #ifndef NDEBUG
955 if( yyTraceFILE ){
956 fprintf(yyTraceFILE,"%sStack Overflow!\n",yyTracePrompt);
957 }
958 #endif
959 while( yypParser->yytos>yypParser->yystack ) yy_pop_parser_stack(yypParser);
960 /* Here code is inserted which will execute if the parser
961 ** stack every overflows */
962 /******** Begin %stack_overflow code ******************************************/
963 /******** End %stack_overflow code ********************************************/
964 RSQueryParser_ARG_STORE /* Suppress warning about unused %extra_argument var */
965 RSQueryParser_CTX_STORE
966 }
967
968 /*
969 ** Print tracing information for a SHIFT action
970 */
971 #ifndef NDEBUG
yyTraceShift(yyParser * yypParser,int yyNewState,const char * zTag)972 static void yyTraceShift(yyParser *yypParser, int yyNewState, const char *zTag){
973 if( yyTraceFILE ){
974 if( yyNewState<YYNSTATE ){
975 fprintf(yyTraceFILE,"%s%s '%s', go to state %d\n",
976 yyTracePrompt, zTag, yyTokenName[yypParser->yytos->major],
977 yyNewState);
978 }else{
979 fprintf(yyTraceFILE,"%s%s '%s', pending reduce %d\n",
980 yyTracePrompt, zTag, yyTokenName[yypParser->yytos->major],
981 yyNewState - YY_MIN_REDUCE);
982 }
983 }
984 }
985 #else
986 # define yyTraceShift(X,Y,Z)
987 #endif
988
989 /*
990 ** Perform a shift action.
991 */
yy_shift(yyParser * yypParser,YYACTIONTYPE yyNewState,YYCODETYPE yyMajor,RSQueryParser_TOKENTYPE yyMinor)992 static void yy_shift(
993 yyParser *yypParser, /* The parser to be shifted */
994 YYACTIONTYPE yyNewState, /* The new state to shift in */
995 YYCODETYPE yyMajor, /* The major token to shift in */
996 RSQueryParser_TOKENTYPE yyMinor /* The minor token to shift in */
997 ){
998 yyStackEntry *yytos;
999 yypParser->yytos++;
1000 #ifdef YYTRACKMAXSTACKDEPTH
1001 if( (int)(yypParser->yytos - yypParser->yystack)>yypParser->yyhwm ){
1002 yypParser->yyhwm++;
1003 assert( yypParser->yyhwm == (int)(yypParser->yytos - yypParser->yystack) );
1004 }
1005 #endif
1006 #if YYSTACKDEPTH>0
1007 if( yypParser->yytos>yypParser->yystackEnd ){
1008 yypParser->yytos--;
1009 yyStackOverflow(yypParser);
1010 return;
1011 }
1012 #else
1013 if( yypParser->yytos>=&yypParser->yystack[yypParser->yystksz] ){
1014 if( yyGrowStack(yypParser) ){
1015 yypParser->yytos--;
1016 yyStackOverflow(yypParser);
1017 return;
1018 }
1019 }
1020 #endif
1021 if( yyNewState > YY_MAX_SHIFT ){
1022 yyNewState += YY_MIN_REDUCE - YY_MIN_SHIFTREDUCE;
1023 }
1024 yytos = yypParser->yytos;
1025 yytos->stateno = yyNewState;
1026 yytos->major = yyMajor;
1027 yytos->minor.yy0 = yyMinor;
1028 yyTraceShift(yypParser, yyNewState, "Shift");
1029 }
1030
1031 /* The following table contains information about every rule that
1032 ** is used during the reduce.
1033 */
1034 static const struct {
1035 YYCODETYPE lhs; /* Symbol on the left-hand side of the rule */
1036 signed char nrhs; /* Negative of the number of RHS symbols in the rule */
1037 } yyRuleInfo[] = {
1038 { 39, -1 }, /* (0) query ::= expr */
1039 { 39, 0 }, /* (1) query ::= */
1040 { 39, -1 }, /* (2) query ::= STAR */
1041 { 27, -2 }, /* (3) expr ::= expr expr */
1042 { 27, -1 }, /* (4) expr ::= union */
1043 { 32, -3 }, /* (5) union ::= expr OR expr */
1044 { 32, -3 }, /* (6) union ::= union OR expr */
1045 { 27, -3 }, /* (7) expr ::= modifier COLON expr */
1046 { 27, -3 }, /* (8) expr ::= modifierlist COLON expr */
1047 { 27, -3 }, /* (9) expr ::= LP expr RP */
1048 { 28, -3 }, /* (10) attribute ::= ATTRIBUTE COLON term */
1049 { 29, -1 }, /* (11) attribute_list ::= attribute */
1050 { 29, -3 }, /* (12) attribute_list ::= attribute_list SEMICOLON attribute */
1051 { 29, -2 }, /* (13) attribute_list ::= attribute_list SEMICOLON */
1052 { 29, 0 }, /* (14) attribute_list ::= */
1053 { 27, -5 }, /* (15) expr ::= expr ARROW LB attribute_list RB */
1054 { 27, -3 }, /* (16) expr ::= QUOTE termlist QUOTE */
1055 { 27, -3 }, /* (17) expr ::= QUOTE term QUOTE */
1056 { 27, -1 }, /* (18) expr ::= term */
1057 { 27, -1 }, /* (19) expr ::= prefix */
1058 { 27, -1 }, /* (20) expr ::= termlist */
1059 { 27, -1 }, /* (21) expr ::= STOPWORD */
1060 { 31, -2 }, /* (22) termlist ::= term term */
1061 { 31, -2 }, /* (23) termlist ::= termlist term */
1062 { 31, -2 }, /* (24) termlist ::= termlist STOPWORD */
1063 { 27, -2 }, /* (25) expr ::= MINUS expr */
1064 { 27, -2 }, /* (26) expr ::= TILDE expr */
1065 { 30, -1 }, /* (27) prefix ::= PREFIX */
1066 { 27, -3 }, /* (28) expr ::= PERCENT term PERCENT */
1067 { 27, -5 }, /* (29) expr ::= PERCENT PERCENT term PERCENT PERCENT */
1068 { 27, -7 }, /* (30) expr ::= PERCENT PERCENT PERCENT term PERCENT PERCENT PERCENT */
1069 { 27, -3 }, /* (31) expr ::= PERCENT STOPWORD PERCENT */
1070 { 27, -5 }, /* (32) expr ::= PERCENT PERCENT STOPWORD PERCENT PERCENT */
1071 { 27, -7 }, /* (33) expr ::= PERCENT PERCENT PERCENT STOPWORD PERCENT PERCENT PERCENT */
1072 { 40, -1 }, /* (34) modifier ::= MODIFIER */
1073 { 36, -3 }, /* (35) modifierlist ::= modifier OR term */
1074 { 36, -3 }, /* (36) modifierlist ::= modifierlist OR term */
1075 { 27, -3 }, /* (37) expr ::= modifier COLON tag_list */
1076 { 34, -2 }, /* (38) tag_list ::= LB term */
1077 { 34, -2 }, /* (39) tag_list ::= LB STOPWORD */
1078 { 34, -2 }, /* (40) tag_list ::= LB prefix */
1079 { 34, -2 }, /* (41) tag_list ::= LB termlist */
1080 { 34, -3 }, /* (42) tag_list ::= tag_list OR term */
1081 { 34, -3 }, /* (43) tag_list ::= tag_list OR STOPWORD */
1082 { 34, -3 }, /* (44) tag_list ::= tag_list OR prefix */
1083 { 34, -3 }, /* (45) tag_list ::= tag_list OR termlist */
1084 { 34, -2 }, /* (46) tag_list ::= tag_list RB */
1085 { 27, -3 }, /* (47) expr ::= modifier COLON numeric_range */
1086 { 38, -4 }, /* (48) numeric_range ::= LSQB num num RSQB */
1087 { 27, -3 }, /* (49) expr ::= modifier COLON geo_filter */
1088 { 35, -6 }, /* (50) geo_filter ::= LSQB num num num TERM RSQB */
1089 { 37, -1 }, /* (51) num ::= NUMBER */
1090 { 37, -2 }, /* (52) num ::= LP num */
1091 { 37, -2 }, /* (53) num ::= MINUS num */
1092 { 41, -1 }, /* (54) term ::= TERM */
1093 { 41, -1 }, /* (55) term ::= NUMBER */
1094 };
1095
1096 static void yy_accept(yyParser*); /* Forward Declaration */
1097
1098 /*
1099 ** Perform a reduce action and the shift that must immediately
1100 ** follow the reduce.
1101 **
1102 ** The yyLookahead and yyLookaheadToken parameters provide reduce actions
1103 ** access to the lookahead token (if any). The yyLookahead will be YYNOCODE
1104 ** if the lookahead token has already been consumed. As this procedure is
1105 ** only called from one place, optimizing compilers will in-line it, which
1106 ** means that the extra parameters have no performance impact.
1107 */
yy_reduce(yyParser * yypParser,unsigned int yyruleno,int yyLookahead,RSQueryParser_TOKENTYPE yyLookaheadToken RSQueryParser_CTX_PDECL)1108 static YYACTIONTYPE yy_reduce(
1109 yyParser *yypParser, /* The parser */
1110 unsigned int yyruleno, /* Number of the rule by which to reduce */
1111 int yyLookahead, /* Lookahead token, or YYNOCODE if none */
1112 RSQueryParser_TOKENTYPE yyLookaheadToken /* Value of the lookahead token */
1113 RSQueryParser_CTX_PDECL /* %extra_context */
1114 ){
1115 int yygoto; /* The next state */
1116 int yyact; /* The next action */
1117 yyStackEntry *yymsp; /* The top of the parser's stack */
1118 int yysize; /* Amount to pop the stack */
1119 RSQueryParser_ARG_FETCH
1120 (void)yyLookahead;
1121 (void)yyLookaheadToken;
1122 yymsp = yypParser->yytos;
1123 #ifndef NDEBUG
1124 if( yyTraceFILE && yyruleno<(int)(sizeof(yyRuleName)/sizeof(yyRuleName[0])) ){
1125 yysize = yyRuleInfo[yyruleno].nrhs;
1126 if( yysize ){
1127 fprintf(yyTraceFILE, "%sReduce %d [%s], go to state %d.\n",
1128 yyTracePrompt,
1129 yyruleno, yyRuleName[yyruleno], yymsp[yysize].stateno);
1130 }else{
1131 fprintf(yyTraceFILE, "%sReduce %d [%s].\n",
1132 yyTracePrompt, yyruleno, yyRuleName[yyruleno]);
1133 }
1134 }
1135 #endif /* NDEBUG */
1136
1137 /* Check that the stack is large enough to grow by a single entry
1138 ** if the RHS of the rule is empty. This ensures that there is room
1139 ** enough on the stack to push the LHS value */
1140 if( yyRuleInfo[yyruleno].nrhs==0 ){
1141 #ifdef YYTRACKMAXSTACKDEPTH
1142 if( (int)(yypParser->yytos - yypParser->yystack)>yypParser->yyhwm ){
1143 yypParser->yyhwm++;
1144 assert( yypParser->yyhwm == (int)(yypParser->yytos - yypParser->yystack));
1145 }
1146 #endif
1147 #if YYSTACKDEPTH>0
1148 if( yypParser->yytos>=yypParser->yystackEnd ){
1149 yyStackOverflow(yypParser);
1150 /* The call to yyStackOverflow() above pops the stack until it is
1151 ** empty, causing the main parser loop to exit. So the return value
1152 ** is never used and does not matter. */
1153 return 0;
1154 }
1155 #else
1156 if( yypParser->yytos>=&yypParser->yystack[yypParser->yystksz-1] ){
1157 if( yyGrowStack(yypParser) ){
1158 yyStackOverflow(yypParser);
1159 /* The call to yyStackOverflow() above pops the stack until it is
1160 ** empty, causing the main parser loop to exit. So the return value
1161 ** is never used and does not matter. */
1162 return 0;
1163 }
1164 yymsp = yypParser->yytos;
1165 }
1166 #endif
1167 }
1168
1169 switch( yyruleno ){
1170 /* Beginning here are the reduction cases. A typical example
1171 ** follows:
1172 ** case 0:
1173 ** #line <lineno> <grammarfile>
1174 ** { ... } // User supplied code
1175 ** #line <lineno> <thisfile>
1176 ** break;
1177 */
1178 /********** Begin reduce actions **********************************************/
1179 YYMINORTYPE yylhsminor;
1180 case 0: /* query ::= expr */
1181 {
1182 /* If the root is a negative node, we intersect it with a wildcard node */
1183
1184 ctx->root = yymsp[0].minor.yy35;
1185
1186 }
1187 break;
1188 case 1: /* query ::= */
1189 {
1190 ctx->root = NULL;
1191 }
1192 break;
1193 case 2: /* query ::= STAR */
1194 {
1195 ctx->root = NewWildcardNode();
1196 }
1197 break;
1198 case 3: /* expr ::= expr expr */
1199 {
1200 int rv = one_not_null(yymsp[-1].minor.yy35, yymsp[0].minor.yy35, (void**)&yylhsminor.yy35);
1201 if (rv == NODENN_BOTH_INVALID) {
1202 yylhsminor.yy35 = NULL;
1203 } else if (rv == NODENN_ONE_NULL) {
1204 // Nothing- `out` is already assigned
1205 } else {
1206 if (yymsp[-1].minor.yy35 && yymsp[-1].minor.yy35->type == QN_PHRASE && yymsp[-1].minor.yy35->pn.exact == 0 &&
1207 yymsp[-1].minor.yy35->opts.fieldMask == RS_FIELDMASK_ALL ) {
1208 yylhsminor.yy35 = yymsp[-1].minor.yy35;
1209 } else {
1210 yylhsminor.yy35 = NewPhraseNode(0);
1211 QueryNode_AddChild(yylhsminor.yy35, yymsp[-1].minor.yy35);
1212 }
1213 QueryNode_AddChild(yylhsminor.yy35, yymsp[0].minor.yy35);
1214 }
1215 }
1216 yymsp[-1].minor.yy35 = yylhsminor.yy35;
1217 break;
1218 case 4: /* expr ::= union */
1219 {
1220 yylhsminor.yy35 = yymsp[0].minor.yy35;
1221 }
1222 yymsp[0].minor.yy35 = yylhsminor.yy35;
1223 break;
1224 case 5: /* union ::= expr OR expr */
1225 {
1226 int rv = one_not_null(yymsp[-2].minor.yy35, yymsp[0].minor.yy35, (void**)&yylhsminor.yy35);
1227 if (rv == NODENN_BOTH_INVALID) {
1228 yylhsminor.yy35 = NULL;
1229 } else if (rv == NODENN_ONE_NULL) {
1230 // Nothing- already assigned
1231 } else {
1232 if (yymsp[-2].minor.yy35->type == QN_UNION && yymsp[-2].minor.yy35->opts.fieldMask == RS_FIELDMASK_ALL) {
1233 yylhsminor.yy35 = yymsp[-2].minor.yy35;
1234 } else {
1235 yylhsminor.yy35 = NewUnionNode();
1236 QueryNode_AddChild(yylhsminor.yy35, yymsp[-2].minor.yy35);
1237 yylhsminor.yy35->opts.fieldMask |= yymsp[-2].minor.yy35->opts.fieldMask;
1238 }
1239
1240 // Handle yymsp[0].minor.yy35
1241 QueryNode_AddChild(yylhsminor.yy35, yymsp[0].minor.yy35);
1242 yylhsminor.yy35->opts.fieldMask |= yymsp[0].minor.yy35->opts.fieldMask;
1243 QueryNode_SetFieldMask(yylhsminor.yy35, yylhsminor.yy35->opts.fieldMask);
1244 }
1245
1246 }
1247 yymsp[-2].minor.yy35 = yylhsminor.yy35;
1248 break;
1249 case 6: /* union ::= union OR expr */
1250 {
1251 yylhsminor.yy35 = yymsp[-2].minor.yy35;
1252 if (yymsp[0].minor.yy35) {
1253 QueryNode_AddChild(yylhsminor.yy35, yymsp[0].minor.yy35);
1254 yylhsminor.yy35->opts.fieldMask |= yymsp[0].minor.yy35->opts.fieldMask;
1255 QueryNode_SetFieldMask(yymsp[0].minor.yy35, yylhsminor.yy35->opts.fieldMask);
1256 }
1257 }
1258 yymsp[-2].minor.yy35 = yylhsminor.yy35;
1259 break;
1260 case 7: /* expr ::= modifier COLON expr */
1261 {
1262 if (yymsp[0].minor.yy35 == NULL) {
1263 yylhsminor.yy35 = NULL;
1264 } else {
1265 if (ctx->sctx->spec) {
1266 QueryNode_SetFieldMask(yymsp[0].minor.yy35, IndexSpec_GetFieldBit(ctx->sctx->spec, yymsp[-2].minor.yy0.s, yymsp[-2].minor.yy0.len));
1267 }
1268 yylhsminor.yy35 = yymsp[0].minor.yy35;
1269 }
1270 }
1271 yymsp[-2].minor.yy35 = yylhsminor.yy35;
1272 break;
1273 case 8: /* expr ::= modifierlist COLON expr */
1274 {
1275
1276 if (yymsp[0].minor.yy35 == NULL) {
1277 yylhsminor.yy35 = NULL;
1278 } else {
1279 //yymsp[0].minor.yy35->opts.fieldMask = 0;
1280 t_fieldMask mask = 0;
1281 if (ctx->sctx->spec) {
1282 for (int i = 0; i < Vector_Size(yymsp[-2].minor.yy78); i++) {
1283 char *p;
1284 Vector_Get(yymsp[-2].minor.yy78, i, &p);
1285 mask |= IndexSpec_GetFieldBit(ctx->sctx->spec, p, strlen(p));
1286 rm_free(p);
1287 }
1288 }
1289 QueryNode_SetFieldMask(yymsp[0].minor.yy35, mask);
1290 Vector_Free(yymsp[-2].minor.yy78);
1291 yylhsminor.yy35=yymsp[0].minor.yy35;
1292 }
1293 }
1294 yymsp[-2].minor.yy35 = yylhsminor.yy35;
1295 break;
1296 case 9: /* expr ::= LP expr RP */
1297 {
1298 yymsp[-2].minor.yy35 = yymsp[-1].minor.yy35;
1299 }
1300 break;
1301 case 10: /* attribute ::= ATTRIBUTE COLON term */
1302 {
1303
1304 yylhsminor.yy55 = (QueryAttribute){ .name = yymsp[-2].minor.yy0.s, .namelen = yymsp[-2].minor.yy0.len, .value = rm_strndup(yymsp[0].minor.yy0.s, yymsp[0].minor.yy0.len), .vallen = yymsp[0].minor.yy0.len };
1305 }
1306 yymsp[-2].minor.yy55 = yylhsminor.yy55;
1307 break;
1308 case 11: /* attribute_list ::= attribute */
1309 {
1310 yylhsminor.yy69 = array_new(QueryAttribute, 2);
1311 yylhsminor.yy69 = array_append(yylhsminor.yy69, yymsp[0].minor.yy55);
1312 }
1313 yymsp[0].minor.yy69 = yylhsminor.yy69;
1314 break;
1315 case 12: /* attribute_list ::= attribute_list SEMICOLON attribute */
1316 {
1317 yylhsminor.yy69 = array_append(yymsp[-2].minor.yy69, yymsp[0].minor.yy55);
1318 }
1319 yymsp[-2].minor.yy69 = yylhsminor.yy69;
1320 break;
1321 case 13: /* attribute_list ::= attribute_list SEMICOLON */
1322 {
1323 yylhsminor.yy69 = yymsp[-1].minor.yy69;
1324 }
1325 yymsp[-1].minor.yy69 = yylhsminor.yy69;
1326 break;
1327 case 14: /* attribute_list ::= */
1328 {
1329 yymsp[1].minor.yy69 = NULL;
1330 }
1331 break;
1332 case 15: /* expr ::= expr ARROW LB attribute_list RB */
1333 {
1334
1335 if (yymsp[-4].minor.yy35 && yymsp[-1].minor.yy69) {
1336 QueryNode_ApplyAttributes(yymsp[-4].minor.yy35, yymsp[-1].minor.yy69, array_len(yymsp[-1].minor.yy69), ctx->status);
1337 }
1338 array_free_ex(yymsp[-1].minor.yy69, rm_free((char*)((QueryAttribute*)ptr )->value));
1339 yylhsminor.yy35 = yymsp[-4].minor.yy35;
1340 }
1341 yymsp[-4].minor.yy35 = yylhsminor.yy35;
1342 break;
1343 case 16: /* expr ::= QUOTE termlist QUOTE */
1344 {
1345 yymsp[-1].minor.yy35->pn.exact =1;
1346 yymsp[-1].minor.yy35->opts.flags |= QueryNode_Verbatim;
1347
1348 yymsp[-2].minor.yy35 = yymsp[-1].minor.yy35;
1349 }
1350 break;
1351 case 17: /* expr ::= QUOTE term QUOTE */
1352 {
1353 yymsp[-2].minor.yy35 = NewTokenNode(ctx, strdupcase(yymsp[-1].minor.yy0.s, yymsp[-1].minor.yy0.len), -1);
1354 yymsp[-2].minor.yy35->opts.flags |= QueryNode_Verbatim;
1355
1356 }
1357 break;
1358 case 18: /* expr ::= term */
1359 {
1360 yylhsminor.yy35 = NewTokenNode(ctx, strdupcase(yymsp[0].minor.yy0.s, yymsp[0].minor.yy0.len), -1);
1361 }
1362 yymsp[0].minor.yy35 = yylhsminor.yy35;
1363 break;
1364 case 19: /* expr ::= prefix */
1365 {
1366 yylhsminor.yy35= yymsp[0].minor.yy35;
1367 }
1368 yymsp[0].minor.yy35 = yylhsminor.yy35;
1369 break;
1370 case 20: /* expr ::= termlist */
1371 {
1372 yylhsminor.yy35 = yymsp[0].minor.yy35;
1373 }
1374 yymsp[0].minor.yy35 = yylhsminor.yy35;
1375 break;
1376 case 21: /* expr ::= STOPWORD */
1377 {
1378 yymsp[0].minor.yy35 = NULL;
1379 }
1380 break;
1381 case 22: /* termlist ::= term term */
1382 {
1383 yylhsminor.yy35 = NewPhraseNode(0);
1384 QueryNode_AddChild(yylhsminor.yy35, NewTokenNode(ctx, strdupcase(yymsp[-1].minor.yy0.s, yymsp[-1].minor.yy0.len), -1));
1385 QueryNode_AddChild(yylhsminor.yy35, NewTokenNode(ctx, strdupcase(yymsp[0].minor.yy0.s, yymsp[0].minor.yy0.len), -1));
1386 }
1387 yymsp[-1].minor.yy35 = yylhsminor.yy35;
1388 break;
1389 case 23: /* termlist ::= termlist term */
1390 {
1391 yylhsminor.yy35 = yymsp[-1].minor.yy35;
1392 QueryNode_AddChild(yylhsminor.yy35, NewTokenNode(ctx, strdupcase(yymsp[0].minor.yy0.s, yymsp[0].minor.yy0.len), -1));
1393 }
1394 yymsp[-1].minor.yy35 = yylhsminor.yy35;
1395 break;
1396 case 24: /* termlist ::= termlist STOPWORD */
1397 case 46: /* tag_list ::= tag_list RB */ yytestcase(yyruleno==46);
1398 {
1399 yylhsminor.yy35 = yymsp[-1].minor.yy35;
1400 }
1401 yymsp[-1].minor.yy35 = yylhsminor.yy35;
1402 break;
1403 case 25: /* expr ::= MINUS expr */
1404 {
1405 if (yymsp[0].minor.yy35) {
1406 yymsp[-1].minor.yy35 = NewNotNode(yymsp[0].minor.yy35);
1407 } else {
1408 yymsp[-1].minor.yy35 = NULL;
1409 }
1410 }
1411 break;
1412 case 26: /* expr ::= TILDE expr */
1413 {
1414 if (yymsp[0].minor.yy35) {
1415 yymsp[-1].minor.yy35 = NewOptionalNode(yymsp[0].minor.yy35);
1416 } else {
1417 yymsp[-1].minor.yy35 = NULL;
1418 }
1419 }
1420 break;
1421 case 27: /* prefix ::= PREFIX */
1422 {
1423 yymsp[0].minor.yy0.s = strdupcase(yymsp[0].minor.yy0.s, yymsp[0].minor.yy0.len);
1424 yylhsminor.yy35 = NewPrefixNode(ctx, yymsp[0].minor.yy0.s, strlen(yymsp[0].minor.yy0.s));
1425 }
1426 yymsp[0].minor.yy35 = yylhsminor.yy35;
1427 break;
1428 case 28: /* expr ::= PERCENT term PERCENT */
1429 case 31: /* expr ::= PERCENT STOPWORD PERCENT */ yytestcase(yyruleno==31);
1430 {
1431 yymsp[-1].minor.yy0.s = strdupcase(yymsp[-1].minor.yy0.s, yymsp[-1].minor.yy0.len);
1432 yymsp[-2].minor.yy35 = NewFuzzyNode(ctx, yymsp[-1].minor.yy0.s, strlen(yymsp[-1].minor.yy0.s), 1);
1433 }
1434 break;
1435 case 29: /* expr ::= PERCENT PERCENT term PERCENT PERCENT */
1436 case 32: /* expr ::= PERCENT PERCENT STOPWORD PERCENT PERCENT */ yytestcase(yyruleno==32);
1437 {
1438 yymsp[-2].minor.yy0.s = strdupcase(yymsp[-2].minor.yy0.s, yymsp[-2].minor.yy0.len);
1439 yymsp[-4].minor.yy35 = NewFuzzyNode(ctx, yymsp[-2].minor.yy0.s, strlen(yymsp[-2].minor.yy0.s), 2);
1440 }
1441 break;
1442 case 30: /* expr ::= PERCENT PERCENT PERCENT term PERCENT PERCENT PERCENT */
1443 case 33: /* expr ::= PERCENT PERCENT PERCENT STOPWORD PERCENT PERCENT PERCENT */ yytestcase(yyruleno==33);
1444 {
1445 yymsp[-3].minor.yy0.s = strdupcase(yymsp[-3].minor.yy0.s, yymsp[-3].minor.yy0.len);
1446 yymsp[-6].minor.yy35 = NewFuzzyNode(ctx, yymsp[-3].minor.yy0.s, strlen(yymsp[-3].minor.yy0.s), 3);
1447 }
1448 break;
1449 case 34: /* modifier ::= MODIFIER */
1450 {
1451 yymsp[0].minor.yy0.len = unescapen((char*)yymsp[0].minor.yy0.s, yymsp[0].minor.yy0.len);
1452 yylhsminor.yy0 = yymsp[0].minor.yy0;
1453 }
1454 yymsp[0].minor.yy0 = yylhsminor.yy0;
1455 break;
1456 case 35: /* modifierlist ::= modifier OR term */
1457 {
1458 yylhsminor.yy78 = NewVector(char *, 2);
1459 char *s = rm_strndup(yymsp[-2].minor.yy0.s, yymsp[-2].minor.yy0.len);
1460 Vector_Push(yylhsminor.yy78, s);
1461 s = rm_strndup(yymsp[0].minor.yy0.s, yymsp[0].minor.yy0.len);
1462 Vector_Push(yylhsminor.yy78, s);
1463 }
1464 yymsp[-2].minor.yy78 = yylhsminor.yy78;
1465 break;
1466 case 36: /* modifierlist ::= modifierlist OR term */
1467 {
1468 char *s = rm_strndup(yymsp[0].minor.yy0.s, yymsp[0].minor.yy0.len);
1469 Vector_Push(yymsp[-2].minor.yy78, s);
1470 yylhsminor.yy78 = yymsp[-2].minor.yy78;
1471 }
1472 yymsp[-2].minor.yy78 = yylhsminor.yy78;
1473 break;
1474 case 37: /* expr ::= modifier COLON tag_list */
1475 {
1476 if (!yymsp[0].minor.yy35) {
1477 yylhsminor.yy35= NULL;
1478 } else {
1479 // Tag field names must be case sensitive, we we can't do strdupcase
1480 char *s = rm_strndup(yymsp[-2].minor.yy0.s, yymsp[-2].minor.yy0.len);
1481 size_t slen = unescapen((char*)s, yymsp[-2].minor.yy0.len);
1482
1483 yylhsminor.yy35 = NewTagNode(s, slen);
1484 QueryNode_AddChildren(yylhsminor.yy35, yymsp[0].minor.yy35->children, QueryNode_NumChildren(yymsp[0].minor.yy35));
1485
1486 // Set the children count on yymsp[0].minor.yy35 to 0 so they won't get recursively free'd
1487 QueryNode_ClearChildren(yymsp[0].minor.yy35, 0);
1488 QueryNode_Free(yymsp[0].minor.yy35);
1489 }
1490 }
1491 yymsp[-2].minor.yy35 = yylhsminor.yy35;
1492 break;
1493 case 38: /* tag_list ::= LB term */
1494 case 39: /* tag_list ::= LB STOPWORD */ yytestcase(yyruleno==39);
1495 {
1496 yymsp[-1].minor.yy35 = NewPhraseNode(0);
1497 QueryNode_AddChild(yymsp[-1].minor.yy35, NewTokenNode(ctx, rm_strndup(yymsp[0].minor.yy0.s, yymsp[0].minor.yy0.len), -1));
1498 }
1499 break;
1500 case 40: /* tag_list ::= LB prefix */
1501 case 41: /* tag_list ::= LB termlist */ yytestcase(yyruleno==41);
1502 {
1503 yymsp[-1].minor.yy35 = NewPhraseNode(0);
1504 QueryNode_AddChild(yymsp[-1].minor.yy35, yymsp[0].minor.yy35);
1505 }
1506 break;
1507 case 42: /* tag_list ::= tag_list OR term */
1508 case 43: /* tag_list ::= tag_list OR STOPWORD */ yytestcase(yyruleno==43);
1509 {
1510 QueryNode_AddChild(yymsp[-2].minor.yy35, NewTokenNode(ctx, rm_strndup(yymsp[0].minor.yy0.s, yymsp[0].minor.yy0.len), -1));
1511 yylhsminor.yy35 = yymsp[-2].minor.yy35;
1512 }
1513 yymsp[-2].minor.yy35 = yylhsminor.yy35;
1514 break;
1515 case 44: /* tag_list ::= tag_list OR prefix */
1516 case 45: /* tag_list ::= tag_list OR termlist */ yytestcase(yyruleno==45);
1517 {
1518 QueryNode_AddChild(yymsp[-2].minor.yy35, yymsp[0].minor.yy35);
1519 yylhsminor.yy35 = yymsp[-2].minor.yy35;
1520 }
1521 yymsp[-2].minor.yy35 = yylhsminor.yy35;
1522 break;
1523 case 47: /* expr ::= modifier COLON numeric_range */
1524 {
1525 // we keep the capitalization as is
1526 yymsp[0].minor.yy36->fieldName = rm_strndup(yymsp[-2].minor.yy0.s, yymsp[-2].minor.yy0.len);
1527 yylhsminor.yy35 = NewNumericNode(yymsp[0].minor.yy36);
1528 }
1529 yymsp[-2].minor.yy35 = yylhsminor.yy35;
1530 break;
1531 case 48: /* numeric_range ::= LSQB num num RSQB */
1532 {
1533 yymsp[-3].minor.yy36 = NewNumericFilter(yymsp[-2].minor.yy83.num, yymsp[-1].minor.yy83.num, yymsp[-2].minor.yy83.inclusive, yymsp[-1].minor.yy83.inclusive);
1534 }
1535 break;
1536 case 49: /* expr ::= modifier COLON geo_filter */
1537 {
1538 // we keep the capitalization as is
1539 yymsp[0].minor.yy64->property = rm_strndup(yymsp[-2].minor.yy0.s, yymsp[-2].minor.yy0.len);
1540 yylhsminor.yy35 = NewGeofilterNode(yymsp[0].minor.yy64);
1541 }
1542 yymsp[-2].minor.yy35 = yylhsminor.yy35;
1543 break;
1544 case 50: /* geo_filter ::= LSQB num num num TERM RSQB */
1545 {
1546 char buf[16] = {0};
1547 if (yymsp[-1].minor.yy0.len < 16) {
1548 memcpy(buf, yymsp[-1].minor.yy0.s, yymsp[-1].minor.yy0.len);
1549 } else {
1550 strcpy(buf, "INVALID");
1551 }
1552 yymsp[-5].minor.yy64 = NewGeoFilter(yymsp[-4].minor.yy83.num, yymsp[-3].minor.yy83.num, yymsp[-2].minor.yy83.num, buf);
1553 GeoFilter_Validate(yymsp[-5].minor.yy64, ctx->status);
1554 }
1555 break;
1556 case 51: /* num ::= NUMBER */
1557 {
1558 yylhsminor.yy83.num = yymsp[0].minor.yy0.numval;
1559 yylhsminor.yy83.inclusive = 1;
1560 }
1561 yymsp[0].minor.yy83 = yylhsminor.yy83;
1562 break;
1563 case 52: /* num ::= LP num */
1564 {
1565 yymsp[-1].minor.yy83=yymsp[0].minor.yy83;
1566 yymsp[-1].minor.yy83.inclusive = 0;
1567 }
1568 break;
1569 case 53: /* num ::= MINUS num */
1570 {
1571 yymsp[0].minor.yy83.num = -yymsp[0].minor.yy83.num;
1572 yymsp[-1].minor.yy83 = yymsp[0].minor.yy83;
1573 }
1574 break;
1575 case 54: /* term ::= TERM */
1576 case 55: /* term ::= NUMBER */ yytestcase(yyruleno==55);
1577 {
1578 yylhsminor.yy0 = yymsp[0].minor.yy0;
1579 }
1580 yymsp[0].minor.yy0 = yylhsminor.yy0;
1581 break;
1582 default:
1583 break;
1584 /********** End reduce actions ************************************************/
1585 };
1586 assert( yyruleno<sizeof(yyRuleInfo)/sizeof(yyRuleInfo[0]) );
1587 yygoto = yyRuleInfo[yyruleno].lhs;
1588 yysize = yyRuleInfo[yyruleno].nrhs;
1589 yyact = yy_find_reduce_action(yymsp[yysize].stateno,(YYCODETYPE)yygoto);
1590
1591 /* There are no SHIFTREDUCE actions on nonterminals because the table
1592 ** generator has simplified them to pure REDUCE actions. */
1593 assert( !(yyact>YY_MAX_SHIFT && yyact<=YY_MAX_SHIFTREDUCE) );
1594
1595 /* It is not possible for a REDUCE to be followed by an error */
1596 assert( yyact!=YY_ERROR_ACTION );
1597
1598 yymsp += yysize+1;
1599 yypParser->yytos = yymsp;
1600 yymsp->stateno = (YYACTIONTYPE)yyact;
1601 yymsp->major = (YYCODETYPE)yygoto;
1602 yyTraceShift(yypParser, yyact, "... then shift");
1603 return yyact;
1604 }
1605
1606 /*
1607 ** The following code executes when the parse fails
1608 */
1609 #ifndef YYNOERRORRECOVERY
yy_parse_failed(yyParser * yypParser)1610 static void yy_parse_failed(
1611 yyParser *yypParser /* The parser */
1612 ){
1613 RSQueryParser_ARG_FETCH
1614 RSQueryParser_CTX_FETCH
1615 #ifndef NDEBUG
1616 if( yyTraceFILE ){
1617 fprintf(yyTraceFILE,"%sFail!\n",yyTracePrompt);
1618 }
1619 #endif
1620 while( yypParser->yytos>yypParser->yystack ) yy_pop_parser_stack(yypParser);
1621 /* Here code is inserted which will be executed whenever the
1622 ** parser fails */
1623 /************ Begin %parse_failure code ***************************************/
1624 /************ End %parse_failure code *****************************************/
1625 RSQueryParser_ARG_STORE /* Suppress warning about unused %extra_argument variable */
1626 RSQueryParser_CTX_STORE
1627 }
1628 #endif /* YYNOERRORRECOVERY */
1629
1630 /*
1631 ** The following code executes when a syntax error first occurs.
1632 */
yy_syntax_error(yyParser * yypParser,int yymajor,RSQueryParser_TOKENTYPE yyminor)1633 static void yy_syntax_error(
1634 yyParser *yypParser, /* The parser */
1635 int yymajor, /* The major type of the error token */
1636 RSQueryParser_TOKENTYPE yyminor /* The minor type of the error token */
1637 ){
1638 RSQueryParser_ARG_FETCH
1639 RSQueryParser_CTX_FETCH
1640 #define TOKEN yyminor
1641 /************ Begin %syntax_error code ****************************************/
1642
1643 QueryError_SetErrorFmt(ctx->status, QUERY_ESYNTAX,
1644 "Syntax error at offset %d near %.*s",
1645 TOKEN.pos, TOKEN.len, TOKEN.s);
1646 /************ End %syntax_error code ******************************************/
1647 RSQueryParser_ARG_STORE /* Suppress warning about unused %extra_argument variable */
1648 RSQueryParser_CTX_STORE
1649 }
1650
1651 /*
1652 ** The following is executed when the parser accepts
1653 */
yy_accept(yyParser * yypParser)1654 static void yy_accept(
1655 yyParser *yypParser /* The parser */
1656 ){
1657 RSQueryParser_ARG_FETCH
1658 RSQueryParser_CTX_FETCH
1659 #ifndef NDEBUG
1660 if( yyTraceFILE ){
1661 fprintf(yyTraceFILE,"%sAccept!\n",yyTracePrompt);
1662 }
1663 #endif
1664 #ifndef YYNOERRORRECOVERY
1665 yypParser->yyerrcnt = -1;
1666 #endif
1667 assert( yypParser->yytos==yypParser->yystack );
1668 /* Here code is inserted which will be executed whenever the
1669 ** parser accepts */
1670 /*********** Begin %parse_accept code *****************************************/
1671 /*********** End %parse_accept code *******************************************/
1672 RSQueryParser_ARG_STORE /* Suppress warning about unused %extra_argument variable */
1673 RSQueryParser_CTX_STORE
1674 }
1675
1676 /* The main parser program.
1677 ** The first argument is a pointer to a structure obtained from
1678 ** "RSQueryParser_Alloc" which describes the current state of the parser.
1679 ** The second argument is the major token number. The third is
1680 ** the minor token. The fourth optional argument is whatever the
1681 ** user wants (and specified in the grammar) and is available for
1682 ** use by the action routines.
1683 **
1684 ** Inputs:
1685 ** <ul>
1686 ** <li> A pointer to the parser (an opaque structure.)
1687 ** <li> The major token number.
1688 ** <li> The minor token number.
1689 ** <li> An option argument of a grammar-specified type.
1690 ** </ul>
1691 **
1692 ** Outputs:
1693 ** None.
1694 */
RSQueryParser_(void * yyp,int yymajor,RSQueryParser_TOKENTYPE yyminor RSQueryParser_ARG_PDECL)1695 void RSQueryParser_(
1696 void *yyp, /* The parser */
1697 int yymajor, /* The major token code number */
1698 RSQueryParser_TOKENTYPE yyminor /* The value for the token */
1699 RSQueryParser_ARG_PDECL /* Optional %extra_argument parameter */
1700 ){
1701 YYMINORTYPE yyminorunion;
1702 YYACTIONTYPE yyact; /* The parser action. */
1703 #if !defined(YYERRORSYMBOL) && !defined(YYNOERRORRECOVERY)
1704 int yyendofinput; /* True if we are at the end of input */
1705 #endif
1706 #ifdef YYERRORSYMBOL
1707 int yyerrorhit = 0; /* True if yymajor has invoked an error */
1708 #endif
1709 yyParser *yypParser = (yyParser*)yyp; /* The parser */
1710 RSQueryParser_CTX_FETCH
1711 RSQueryParser_ARG_STORE
1712
1713 assert( yypParser->yytos!=0 );
1714 #if !defined(YYERRORSYMBOL) && !defined(YYNOERRORRECOVERY)
1715 yyendofinput = (yymajor==0);
1716 #endif
1717
1718 yyact = yypParser->yytos->stateno;
1719 #ifndef NDEBUG
1720 if( yyTraceFILE ){
1721 if( yyact < YY_MIN_REDUCE ){
1722 fprintf(yyTraceFILE,"%sInput '%s' in state %d\n",
1723 yyTracePrompt,yyTokenName[yymajor],yyact);
1724 }else{
1725 fprintf(yyTraceFILE,"%sInput '%s' with pending reduce %d\n",
1726 yyTracePrompt,yyTokenName[yymajor],yyact-YY_MIN_REDUCE);
1727 }
1728 }
1729 #endif
1730
1731 do{
1732 assert( yyact==yypParser->yytos->stateno );
1733 yyact = yy_find_shift_action(yymajor,yyact);
1734 if( yyact >= YY_MIN_REDUCE ){
1735 yyact = yy_reduce(yypParser,yyact-YY_MIN_REDUCE,yymajor,
1736 yyminor RSQueryParser_CTX_PARAM);
1737 }else if( yyact <= YY_MAX_SHIFTREDUCE ){
1738 yy_shift(yypParser,yyact,yymajor,yyminor);
1739 #ifndef YYNOERRORRECOVERY
1740 yypParser->yyerrcnt--;
1741 #endif
1742 break;
1743 }else if( yyact==YY_ACCEPT_ACTION ){
1744 yypParser->yytos--;
1745 yy_accept(yypParser);
1746 return;
1747 }else{
1748 assert( yyact == YY_ERROR_ACTION );
1749 yyminorunion.yy0 = yyminor;
1750 #ifdef YYERRORSYMBOL
1751 int yymx;
1752 #endif
1753 #ifndef NDEBUG
1754 if( yyTraceFILE ){
1755 fprintf(yyTraceFILE,"%sSyntax Error!\n",yyTracePrompt);
1756 }
1757 #endif
1758 #ifdef YYERRORSYMBOL
1759 /* A syntax error has occurred.
1760 ** The response to an error depends upon whether or not the
1761 ** grammar defines an error token "ERROR".
1762 **
1763 ** This is what we do if the grammar does define ERROR:
1764 **
1765 ** * Call the %syntax_error function.
1766 **
1767 ** * Begin popping the stack until we enter a state where
1768 ** it is legal to shift the error symbol, then shift
1769 ** the error symbol.
1770 **
1771 ** * Set the error count to three.
1772 **
1773 ** * Begin accepting and shifting new tokens. No new error
1774 ** processing will occur until three tokens have been
1775 ** shifted successfully.
1776 **
1777 */
1778 if( yypParser->yyerrcnt<0 ){
1779 yy_syntax_error(yypParser,yymajor,yyminor);
1780 }
1781 yymx = yypParser->yytos->major;
1782 if( yymx==YYERRORSYMBOL || yyerrorhit ){
1783 #ifndef NDEBUG
1784 if( yyTraceFILE ){
1785 fprintf(yyTraceFILE,"%sDiscard input token %s\n",
1786 yyTracePrompt,yyTokenName[yymajor]);
1787 }
1788 #endif
1789 yy_destructor(yypParser, (YYCODETYPE)yymajor, &yyminorunion);
1790 yymajor = YYNOCODE;
1791 }else{
1792 while( yypParser->yytos >= yypParser->yystack
1793 && yymx != YYERRORSYMBOL
1794 && (yyact = yy_find_reduce_action(
1795 yypParser->yytos->stateno,
1796 YYERRORSYMBOL)) >= YY_MIN_REDUCE
1797 ){
1798 yy_pop_parser_stack(yypParser);
1799 }
1800 if( yypParser->yytos < yypParser->yystack || yymajor==0 ){
1801 yy_destructor(yypParser,(YYCODETYPE)yymajor,&yyminorunion);
1802 yy_parse_failed(yypParser);
1803 #ifndef YYNOERRORRECOVERY
1804 yypParser->yyerrcnt = -1;
1805 #endif
1806 yymajor = YYNOCODE;
1807 }else if( yymx!=YYERRORSYMBOL ){
1808 yy_shift(yypParser,yyact,YYERRORSYMBOL,yyminor);
1809 }
1810 }
1811 yypParser->yyerrcnt = 3;
1812 yyerrorhit = 1;
1813 if( yymajor==YYNOCODE ) break;
1814 yyact = yypParser->yytos->stateno;
1815 #elif defined(YYNOERRORRECOVERY)
1816 /* If the YYNOERRORRECOVERY macro is defined, then do not attempt to
1817 ** do any kind of error recovery. Instead, simply invoke the syntax
1818 ** error routine and continue going as if nothing had happened.
1819 **
1820 ** Applications can set this macro (for example inside %include) if
1821 ** they intend to abandon the parse upon the first syntax error seen.
1822 */
1823 yy_syntax_error(yypParser,yymajor, yyminor);
1824 yy_destructor(yypParser,(YYCODETYPE)yymajor,&yyminorunion);
1825 break;
1826 #else /* YYERRORSYMBOL is not defined */
1827 /* This is what we do if the grammar does not define ERROR:
1828 **
1829 ** * Report an error message, and throw away the input token.
1830 **
1831 ** * If the input token is $, then fail the parse.
1832 **
1833 ** As before, subsequent error messages are suppressed until
1834 ** three input tokens have been successfully shifted.
1835 */
1836 if( yypParser->yyerrcnt<=0 ){
1837 yy_syntax_error(yypParser,yymajor, yyminor);
1838 }
1839 yypParser->yyerrcnt = 3;
1840 yy_destructor(yypParser,(YYCODETYPE)yymajor,&yyminorunion);
1841 if( yyendofinput ){
1842 yy_parse_failed(yypParser);
1843 #ifndef YYNOERRORRECOVERY
1844 yypParser->yyerrcnt = -1;
1845 #endif
1846 }
1847 break;
1848 #endif
1849 }
1850 }while( yypParser->yytos>yypParser->yystack );
1851 #ifndef NDEBUG
1852 if( yyTraceFILE ){
1853 yyStackEntry *i;
1854 char cDiv = '[';
1855 fprintf(yyTraceFILE,"%sReturn. Stack=",yyTracePrompt);
1856 for(i=&yypParser->yystack[1]; i<=yypParser->yytos; i++){
1857 fprintf(yyTraceFILE,"%c%s", cDiv, yyTokenName[i->major]);
1858 cDiv = ' ';
1859 }
1860 fprintf(yyTraceFILE,"]\n");
1861 }
1862 #endif
1863 return;
1864 }
1865