Merge branch release-4-6 into release-5-0
[alexxy/gromacs.git] / src / gromacs / selection / parser.y
1 %code requires {
2 /*
3  * This file is part of the GROMACS molecular simulation package.
4  *
5  * Copyright (c) 2009,2010,2011,2012,2013,2014, by the GROMACS development team, led by
6  * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
7  * and including many others, as listed in the AUTHORS file in the
8  * top-level source directory and at http://www.gromacs.org.
9  *
10  * GROMACS is free software; you can redistribute it and/or
11  * modify it under the terms of the GNU Lesser General Public License
12  * as published by the Free Software Foundation; either version 2.1
13  * of the License, or (at your option) any later version.
14  *
15  * GROMACS is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
18  * Lesser General Public License for more details.
19  *
20  * You should have received a copy of the GNU Lesser General Public
21  * License along with GROMACS; if not, see
22  * http://www.gnu.org/licenses, or write to the Free Software Foundation,
23  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA.
24  *
25  * If you want to redistribute modifications to GROMACS, please
26  * consider that scientific software is very special. Version
27  * control is crucial - bugs must be traceable. We will be happy to
28  * consider code for inclusion in the official distribution, but
29  * derived work must not be called official GROMACS. Details are found
30  * in the README & COPYING files - if they are missing, get the
31  * official version at http://www.gromacs.org.
32  *
33  * To help us fund GROMACS development, we humbly ask that you cite
34  * the research papers on the package. Check out http://www.gromacs.org.
35  */
36 }
37 /*! \internal \file
38  * \brief Grammar description and parser for the selection language.
39  *
40  * \author Teemu Murtola <teemu.murtola@gmail.com>
41  * \ingroup module_selection
42  */
43 %{
44 /*! \internal \file parser.cpp
45  * \brief Generated (from parser.y by Bison) parser for the selection language.
46  *
47  * \ingroup module_selection
48  */
49 /*! \internal \file parser.h
50  * \brief Generated (from parser.y by Bison) parser include file.
51  *
52  * \ingroup module_selection
53  */
54 #include "gromacs/utility/scoped_ptr_sfree.h"
55
56 #include "parser_internal.h"
57
58 using gmx::scoped_ptr_sfree;
59 using gmx::SelectionParserValue;
60 using gmx::SelectionParserValueList;
61 using gmx::SelectionParserValueListPointer;
62 using gmx::SelectionParserParameter;
63 using gmx::SelectionParserParameterList;
64 using gmx::SelectionParserParameterListPointer;
65 using gmx::SelectionTreeElement;
66 using gmx::SelectionTreeElementPointer;
67
68 #ifdef _MSC_VER
69 #pragma warning(disable: 4065)
70 #endif
71 %}
72
73 %code requires{
74 #include "parsetree.h"
75 #include "selelem.h"
76 }
77
78 %union{
79     int                         i;
80     real                        r;
81     char                       *str;
82     struct gmx_ana_selmethod_t *meth;
83
84     gmx::SelectionStringMatchType                smt;
85
86     gmx::SelectionTreeElementPointer            *sel;
87     gmx::SelectionParserValue                   *val;
88     gmx::SelectionParserValueListPointer        *vlist;
89     gmx::SelectionParserParameter               *param;
90     gmx::SelectionParserParameterListPointer    *plist;
91 };
92
93 /* Invalid token to report lexer errors */
94 %token INVALID
95
96 /* Simple input tokens */
97 %token <i>     TOK_INT
98 %token <r>     TOK_REAL
99 %token <str>   STR
100 %token <str>   IDENTIFIER
101 %token         CMD_SEP
102
103 /* Simple keyword tokens */
104 %token         GROUP
105 %token         TO
106
107 /* Variable tokens */
108 %token <sel>   VARIABLE_NUMERIC
109 %token <sel>   VARIABLE_GROUP
110 %token <sel>   VARIABLE_POS
111
112 /* Selection method tokens */
113 %token <meth>  KEYWORD_NUMERIC
114 %token <meth>  KEYWORD_STR
115 %token <str>   KEYWORD_POS
116 %token <meth>  KEYWORD_GROUP
117 %token <meth>  METHOD_NUMERIC
118 %token <meth>  METHOD_GROUP
119 %token <meth>  METHOD_POS
120 %token <meth>  MODIFIER
121 /* Empty token that should precede any non-position KEYWORD/METHOD token that
122  * is not preceded by KEYWORD_POS. This is used to work around reduce/reduce
123  * conflicts that appear when a lookahead token would require a reduction of
124  * a rule with empty RHS before shifting, and there is an alternative reduction
125  * available. Replacing the empty RHS with a dummy token makes these conflicts
126  * only shift/reduce conflicts. Another alternative would be to remove the
127  * pos_mod non-terminal completely and split each rule that uses it into two,
128  * but this would require duplicating six rules in the grammar. */
129 %token         EMPTY_POSMOD
130
131 %token <str>   PARAM
132 %token         END_OF_METHOD
133
134 %token          OF
135 /* Comparison operators have lower precedence than parameter reduction
136  * to make it possible to parse, e.g., "mindist from resnr 1 < 2" without
137  * parenthesis. */
138 %nonassoc <str> CMP_OP
139 /* A dummy token that determines the precedence of parameter reduction */
140 %nonassoc       PARAM_REDUCT
141 /* Boolean operator tokens */
142 %left           OR XOR
143 %left           AND
144 %left           NOT
145 /* Arithmetic operator tokens */
146 %left           '+' '-'
147 %left           '*' '/'
148 %right          UNARY_NEG   /* Dummy token for unary negation precedence */
149 %right          '^'
150 %nonassoc       NUM_REDUCT  /* Dummy token for numerical keyword reduction precedence */
151
152 /* Simple non-terminals */
153 %type <i>     integer_number
154 %type <r>     real_number number
155 %type <str>   string
156 %type <str>   pos_mod
157 %type <smt>   str_match_type
158
159 /* Expression non-terminals */
160 %type <sel>   commands command cmd_plain
161 %type <sel>   selection
162 %type <sel>   sel_expr
163 %type <sel>   num_expr
164 %type <sel>   str_expr
165 %type <sel>   pos_expr
166
167 /* Parameter/value non-terminals */
168 %type <plist> method_params method_param_list
169 %type <param> method_param
170 %type <vlist> value_list value_list_contents basic_value_list basic_value_list_contents
171 %type <val>   value_item value_item_range basic_value_item
172
173 %destructor { free($$);        } STR IDENTIFIER KEYWORD_POS CMP_OP string
174 %destructor { if($$) free($$); } PARAM pos_mod
175 %destructor { delete $$;       } commands command cmd_plain selection
176 %destructor { delete $$;       } sel_expr num_expr str_expr pos_expr
177 %destructor { delete $$;       } method_params method_param_list method_param
178 %destructor { delete $$;       } value_list value_list_contents basic_value_list basic_value_list_contents
179 %destructor { delete $$;       } value_item value_item_range basic_value_item
180
181 %expect 35
182 %debug
183 %pure-parser
184 %define api.push-pull push
185
186 %name-prefix="_gmx_sel_yy"
187 %parse-param { void *scanner }
188
189 %%
190
191 /* The start rule: allow one or more commands */
192 commands:    /* empty */
193              {
194                  BEGIN_ACTION;
195                  set_empty($$);
196                  END_ACTION;
197              }
198            | commands command
199              {
200                  BEGIN_ACTION;
201                  set($$, _gmx_sel_append_selection(get($2), get($1), scanner));
202                  if (_gmx_sel_parser_should_finish(scanner))
203                      YYACCEPT;
204                  END_ACTION;
205              }
206 ;
207
208 /* A command is formed from an actual command and a separator */
209 command:     cmd_plain CMD_SEP  { $$ = $1; }
210            | error CMD_SEP
211              {
212                  BEGIN_ACTION;
213                  _gmx_selparser_error(scanner, "invalid selection '%s'",
214                                       _gmx_sel_lexer_pselstr(scanner));
215                  _gmx_sel_lexer_clear_method_stack(scanner);
216                  if (_gmx_sel_is_lexer_interactive(scanner))
217                  {
218                      _gmx_sel_lexer_clear_pselstr(scanner);
219                      yyerrok;
220                  }
221                  else
222                  {
223                      YYABORT;
224                  }
225                  set_empty($$);
226                  END_ACTION;
227              }
228 ;
229
230 /* Commands can be selections or variable assignments */
231 cmd_plain:   /* empty */
232              {
233                  BEGIN_ACTION;
234                  set_empty($$);
235                  END_ACTION;
236              }
237            | TOK_INT
238              {
239                  BEGIN_ACTION;
240                  SelectionTreeElementPointer s
241                         = _gmx_sel_init_group_by_id($1, scanner);
242                  SelectionTreeElementPointer p
243                         = _gmx_sel_init_position(s, NULL, scanner);
244                  if (!p) YYERROR;
245                  set($$, _gmx_sel_init_selection(NULL, p, scanner));
246                  END_ACTION;
247              }
248            | string
249              {
250                  BEGIN_ACTION;
251                  scoped_ptr_sfree nameGuard($1);
252                  SelectionTreeElementPointer s
253                         = _gmx_sel_init_group_by_name($1, scanner);
254                  SelectionTreeElementPointer p
255                         = _gmx_sel_init_position(s, NULL, scanner);
256                  if (!p) YYERROR;
257                  set($$, _gmx_sel_init_selection(NULL, p, scanner));
258                  END_ACTION;
259              }
260            | selection
261              {
262                  BEGIN_ACTION;
263                  set($$, _gmx_sel_init_selection(NULL, get($1), scanner));
264                  END_ACTION;
265              }
266            | string selection
267              {
268                  BEGIN_ACTION;
269                  scoped_ptr_sfree nameGuard($1);
270                  set($$, _gmx_sel_init_selection($1, get($2), scanner));
271                  END_ACTION;
272              }
273            | IDENTIFIER '=' sel_expr
274              {
275                  BEGIN_ACTION;
276                  scoped_ptr_sfree nameGuard($1);
277                  set($$, _gmx_sel_assign_variable($1, get($3), scanner));
278                  END_ACTION;
279              }
280            | IDENTIFIER '=' num_expr
281              {
282                  BEGIN_ACTION;
283                  scoped_ptr_sfree nameGuard($1);
284                  set($$, _gmx_sel_assign_variable($1, get($3), scanner));
285                  END_ACTION;
286              }
287            | IDENTIFIER '=' pos_expr
288              {
289                  BEGIN_ACTION;
290                  scoped_ptr_sfree nameGuard($1);
291                  set($$, _gmx_sel_assign_variable($1, get($3), scanner));
292                  END_ACTION;
293              }
294 ;
295
296 /* Selection is made of an expression and zero or more modifiers */
297 selection:   pos_expr           { $$ = $1; }
298            | sel_expr
299              {
300                  BEGIN_ACTION;
301                  set($$, _gmx_sel_init_position(get($1), NULL, scanner));
302                  CHECK_SEL($$);
303                  END_ACTION;
304              }
305            | '(' selection ')'  { $$ = $2; }
306            | selection MODIFIER method_params
307              {
308                  BEGIN_ACTION;
309                  set($$, _gmx_sel_init_modifier($2, get($3), get($1), scanner));
310                  CHECK_SEL($$);
311                  END_ACTION;
312              }
313 ;
314
315 /********************************************************************
316  * BASIC NON-TERMINAL SYMBOLS
317  ********************************************************************/
318
319 integer_number:
320              TOK_INT            { $$ = $1; }
321            | '-' TOK_INT        { $$ = -$2; }
322 ;
323
324 real_number:
325              TOK_REAL           { $$ = $1; }
326            | '-' TOK_REAL       { $$ = -$2; }
327 ;
328
329 number:      integer_number     { $$ = $1; }
330            | real_number        { $$ = $1; }
331 ;
332
333 string:      STR                { $$ = $1; }
334            | IDENTIFIER         { $$ = $1; }
335 ;
336
337 /********************************************************************
338  * ATOM SELECTION EXPRESSIONS
339  ********************************************************************/
340
341 /* Boolean expressions and grouping */
342 sel_expr:    NOT sel_expr
343              {
344                  BEGIN_ACTION;
345                  SelectionTreeElementPointer arg(get($2));
346                  SelectionTreeElementPointer sel(
347                         new SelectionTreeElement(SEL_BOOLEAN));
348                  sel->u.boolt = BOOL_NOT;
349                  sel->child = arg;
350                  set($$, sel);
351                  END_ACTION;
352              }
353            | sel_expr AND sel_expr
354              {
355                  BEGIN_ACTION;
356                  SelectionTreeElementPointer arg1(get($1)), arg2(get($3));
357                  SelectionTreeElementPointer sel(
358                         new SelectionTreeElement(SEL_BOOLEAN));
359                  sel->u.boolt = BOOL_AND;
360                  sel->child = arg1; sel->child->next = arg2;
361                  set($$, sel);
362                  END_ACTION;
363              }
364            | sel_expr OR  sel_expr
365              {
366                  BEGIN_ACTION;
367                  SelectionTreeElementPointer arg1(get($1)), arg2(get($3));
368                  SelectionTreeElementPointer sel(
369                         new SelectionTreeElement(SEL_BOOLEAN));
370                  sel->u.boolt = BOOL_OR;
371                  sel->child = arg1; sel->child->next = arg2;
372                  set($$, sel);
373                  END_ACTION;
374              }
375            | '(' sel_expr ')'   { $$ = $2; }
376 ;
377
378 /* Numeric comparisons */
379 sel_expr:    num_expr CMP_OP num_expr
380              {
381                  BEGIN_ACTION;
382                  scoped_ptr_sfree opGuard($2);
383                  set($$, _gmx_sel_init_comparison(get($1), get($3), $2, scanner));
384                  CHECK_SEL($$);
385                  END_ACTION;
386              }
387 ;
388
389 /* External groups */
390 sel_expr:    GROUP string
391              {
392                  BEGIN_ACTION;
393                  scoped_ptr_sfree nameGuard($2);
394                  set($$, _gmx_sel_init_group_by_name($2, scanner));
395                  END_ACTION;
396              }
397            | GROUP TOK_INT
398              {
399                  BEGIN_ACTION;
400                  set($$, _gmx_sel_init_group_by_id($2, scanner));
401                  END_ACTION;
402              }
403 ;
404
405 /* Position modifiers for selection methods */
406 pos_mod:     EMPTY_POSMOD       { $$ = NULL; }
407            | KEYWORD_POS        { $$ = $1;   }
408 ;
409
410 /* Matching mode forcing for keyword matching */
411 str_match_type:
412              '~'                { $$ = gmx::eStringMatchType_RegularExpression; }
413            | '?'                { $$ = gmx::eStringMatchType_Wildcard; }
414            | '='                { $$ = gmx::eStringMatchType_Exact; }
415 ;
416
417 /* Keyword selections */
418 sel_expr:    pos_mod KEYWORD_GROUP
419              {
420                  BEGIN_ACTION;
421                  scoped_ptr_sfree posmodGuard($1);
422                  set($$, _gmx_sel_init_keyword($2, SelectionParserValueListPointer(), $1, scanner));
423                  CHECK_SEL($$);
424                  END_ACTION;
425              }
426            | pos_mod KEYWORD_STR basic_value_list
427              {
428                  BEGIN_ACTION;
429                  scoped_ptr_sfree posmodGuard($1);
430                  set($$, _gmx_sel_init_keyword_strmatch($2, gmx::eStringMatchType_Auto, get($3), $1, scanner));
431                  CHECK_SEL($$);
432                  END_ACTION;
433              }
434            | pos_mod KEYWORD_STR str_match_type basic_value_list
435              {
436                  BEGIN_ACTION;
437                  scoped_ptr_sfree posmodGuard($1);
438                  set($$, _gmx_sel_init_keyword_strmatch($2, $3, get($4), $1, scanner));
439                  CHECK_SEL($$);
440                  END_ACTION;
441              }
442            | pos_mod KEYWORD_NUMERIC basic_value_list
443              {
444                  BEGIN_ACTION;
445                  scoped_ptr_sfree posmodGuard($1);
446                  set($$, _gmx_sel_init_keyword($2, get($3), $1, scanner));
447                  CHECK_SEL($$);
448                  END_ACTION;
449              }
450 ;
451
452 /* Custom selection methods */
453 sel_expr:    pos_mod METHOD_GROUP method_params
454              {
455                  BEGIN_ACTION;
456                  scoped_ptr_sfree posmodGuard($1);
457                  set($$, _gmx_sel_init_method($2, get($3), $1, scanner));
458                  CHECK_SEL($$);
459                  END_ACTION;
460              }
461 ;
462
463 /********************************************************************
464  * NUMERICAL EXPRESSIONS
465  ********************************************************************/
466
467 /* Basic numerical values */
468 num_expr:    TOK_INT
469              {
470                  BEGIN_ACTION;
471                  SelectionTreeElementPointer sel(
472                         new SelectionTreeElement(SEL_CONST));
473                  _gmx_selelem_set_vtype(sel, INT_VALUE);
474                  _gmx_selvalue_reserve(&sel->v, 1);
475                  sel->v.u.i[0] = $1;
476                  set($$, sel);
477                  END_ACTION;
478              }
479            | TOK_REAL
480              {
481                  BEGIN_ACTION;
482                  SelectionTreeElementPointer sel(
483                         new SelectionTreeElement(SEL_CONST));
484                  _gmx_selelem_set_vtype(sel, REAL_VALUE);
485                  _gmx_selvalue_reserve(&sel->v, 1);
486                  sel->v.u.r[0] = $1;
487                  set($$, sel);
488                  END_ACTION;
489              }
490 ;
491
492 /* Numeric selection methods */
493 num_expr:    pos_mod KEYWORD_NUMERIC    %prec NUM_REDUCT
494              {
495                  BEGIN_ACTION;
496                  scoped_ptr_sfree posmodGuard($1);
497                  set($$, _gmx_sel_init_keyword($2, SelectionParserValueListPointer(), $1, scanner));
498                  CHECK_SEL($$);
499                  END_ACTION;
500              }
501            | pos_mod METHOD_NUMERIC method_params
502              {
503                  BEGIN_ACTION;
504                  scoped_ptr_sfree posmodGuard($1);
505                  set($$, _gmx_sel_init_method($2, get($3), $1, scanner));
506                  CHECK_SEL($$);
507                  END_ACTION;
508              }
509 ;
510
511 /* Arithmetic evaluation and grouping */
512 num_expr:    num_expr '+' num_expr
513              {
514                  BEGIN_ACTION;
515                  set($$, _gmx_sel_init_arithmetic(get($1), get($3), '+', scanner));
516                  END_ACTION;
517              }
518            | num_expr '-' num_expr
519              {
520                  BEGIN_ACTION;
521                  set($$, _gmx_sel_init_arithmetic(get($1), get($3), '-', scanner));
522                  END_ACTION;
523              }
524            | num_expr '*' num_expr
525              {
526                  BEGIN_ACTION;
527                  set($$, _gmx_sel_init_arithmetic(get($1), get($3), '*', scanner));
528                  END_ACTION;
529              }
530            | num_expr '/' num_expr
531              {
532                  BEGIN_ACTION;
533                  set($$, _gmx_sel_init_arithmetic(get($1), get($3), '/', scanner));
534                  END_ACTION;
535              }
536            | '-' num_expr %prec UNARY_NEG
537              {
538                  BEGIN_ACTION;
539                  set($$, _gmx_sel_init_arithmetic(get($2), SelectionTreeElementPointer(), '-', scanner));
540                  END_ACTION;
541              }
542            | num_expr '^' num_expr
543              {
544                  BEGIN_ACTION;
545                  set($$, _gmx_sel_init_arithmetic(get($1), get($3), '^', scanner));
546                  END_ACTION;
547              }
548            | '(' num_expr ')'   { $$ = $2; }
549 ;
550
551 /********************************************************************
552  * STRING EXPRESSIONS
553  ********************************************************************/
554
555 str_expr:    string
556              {
557                  BEGIN_ACTION;
558                  SelectionTreeElementPointer sel(
559                         new SelectionTreeElement(SEL_CONST));
560                  _gmx_selelem_set_vtype(sel, STR_VALUE);
561                  _gmx_selvalue_reserve(&sel->v, 1);
562                  sel->v.u.s[0] = $1;
563                  set($$, sel);
564                  END_ACTION;
565              }
566            | pos_mod KEYWORD_STR
567              {
568                  BEGIN_ACTION;
569                  scoped_ptr_sfree posmodGuard($1);
570                  set($$, _gmx_sel_init_keyword($2, SelectionParserValueListPointer(), $1, scanner));
571                  CHECK_SEL($$);
572                  END_ACTION;
573              }
574 ;
575
576 /********************************************************************
577  * POSITION EXPRESSIONS
578  ********************************************************************/
579
580 /* Constant position expressions */
581 pos_expr:    '[' number ',' number ',' number ']'
582              {
583                  BEGIN_ACTION;
584                  set($$, _gmx_sel_init_const_position($2, $4, $6));
585                  END_ACTION;
586              }
587 ;
588
589 /* Grouping of position expressions */
590 pos_expr:    '(' pos_expr ')'   { $$ = $2; }
591 ;
592
593 /* Expressions with a position value */
594 pos_expr:    METHOD_POS method_params
595              {
596                  BEGIN_ACTION;
597                  set($$, _gmx_sel_init_method($1, get($2), NULL, scanner));
598                  CHECK_SEL($$);
599                  END_ACTION;
600              }
601 ;
602
603 /* Evaluation of positions using a keyword */
604 pos_expr:    KEYWORD_POS OF sel_expr    %prec PARAM_REDUCT
605              {
606                  BEGIN_ACTION;
607                  scoped_ptr_sfree keywordGuard($1);
608                  set($$, _gmx_sel_init_position(get($3), $1, scanner));
609                  CHECK_SEL($$);
610                  END_ACTION;
611              }
612 ;
613
614 /********************************************************************
615  * VARIABLES
616  ********************************************************************/
617
618 sel_expr:    VARIABLE_GROUP
619              {
620                  BEGIN_ACTION;
621                  set($$, _gmx_sel_init_variable_ref(get($1)));
622                  END_ACTION;
623              }
624 ;
625
626 num_expr:    VARIABLE_NUMERIC
627              {
628                  BEGIN_ACTION;
629                  set($$, _gmx_sel_init_variable_ref(get($1)));
630                  END_ACTION;
631              }
632 ;
633
634 pos_expr:    VARIABLE_POS
635              {
636                  BEGIN_ACTION;
637                  set($$, _gmx_sel_init_variable_ref(get($1)));
638                  END_ACTION;
639              }
640 ;
641
642 /********************************************************************
643  * METHOD PARAMETERS
644  ********************************************************************/
645
646 method_params:
647              method_param_list
648              { $$ = $1; }
649            | method_param_list END_OF_METHOD
650              { $$ = $1; }
651 ;
652
653 method_param_list:
654              /* empty */
655              {
656                  BEGIN_ACTION;
657                  set($$, SelectionParserParameter::createList());
658                  END_ACTION;
659              }
660            | method_param_list method_param
661              {
662                  BEGIN_ACTION;
663                  SelectionParserParameterListPointer list(get($1));
664                  list->push_back(get($2));
665                  set($$, move(list));
666                  END_ACTION;
667              }
668 ;
669
670 method_param:
671              PARAM value_list
672              {
673                  BEGIN_ACTION;
674                  scoped_ptr_sfree nameGuard($1);
675                  set($$, SelectionParserParameter::create($1, get($2)));
676                  END_ACTION;
677              }
678 ;
679
680 value_list:  value_list_contents                 { $$ = $1;   }
681            | '{' value_list_contents '}'         { $$ = $2;   }
682 ;
683
684 value_list_contents:
685              /* empty */
686              {
687                  BEGIN_ACTION;
688                  set($$, SelectionParserValue::createList());
689                  END_ACTION;
690              }
691            | value_list_contents value_item
692              {
693                  BEGIN_ACTION;
694                  SelectionParserValueListPointer list(get($1));
695                  list->push_back(get($2));
696                  set($$, move(list));
697                  END_ACTION;
698              }
699            | value_list_contents ',' value_item
700              {
701                  BEGIN_ACTION;
702                  SelectionParserValueListPointer list(get($1));
703                  list->push_back(get($3));
704                  set($$, move(list));
705                  END_ACTION;
706              }
707 ;
708
709 basic_value_list:
710              basic_value_list_contents           { $$ = $1; }
711            | '{' basic_value_list_contents '}'   { $$ = $2; }
712 ;
713
714 basic_value_list_contents:
715              basic_value_item
716              {
717                  BEGIN_ACTION;
718                  set($$, SelectionParserValue::createList(get($1)));
719                  END_ACTION;
720              }
721            | basic_value_list_contents basic_value_item
722              {
723                  BEGIN_ACTION;
724                  SelectionParserValueListPointer list(get($1));
725                  list->push_back(get($2));
726                  set($$, move(list));
727                  END_ACTION;
728              }
729            | basic_value_list_contents ',' basic_value_item
730              {
731                  BEGIN_ACTION;
732                  SelectionParserValueListPointer list(get($1));
733                  list->push_back(get($3));
734                  set($$, move(list));
735                  END_ACTION;
736              }
737 ;
738
739 value_item:  sel_expr            %prec PARAM_REDUCT
740              {
741                  BEGIN_ACTION;
742                  set($$, SelectionParserValue::createExpr(get($1)));
743                  END_ACTION;
744              }
745            | pos_expr            %prec PARAM_REDUCT
746              {
747                  BEGIN_ACTION;
748                  set($$, SelectionParserValue::createExpr(get($1)));
749                  END_ACTION;
750              }
751            | num_expr            %prec PARAM_REDUCT
752              {
753                  BEGIN_ACTION;
754                  set($$, SelectionParserValue::createExpr(get($1)));
755                  END_ACTION;
756              }
757            | str_expr            %prec PARAM_REDUCT
758              {
759                  BEGIN_ACTION;
760                  set($$, SelectionParserValue::createExpr(get($1)));
761                  END_ACTION;
762              }
763            | value_item_range    { $$ = $1; }
764 ;
765
766 basic_value_item:
767              integer_number      %prec PARAM_REDUCT
768              {
769                  BEGIN_ACTION;
770                  set($$, SelectionParserValue::createInteger($1));
771                  END_ACTION;
772              }
773            | real_number         %prec PARAM_REDUCT
774              {
775                  BEGIN_ACTION;
776                  set($$, SelectionParserValue::createReal($1));
777                  END_ACTION;
778              }
779            | string              %prec PARAM_REDUCT
780              {
781                  BEGIN_ACTION;
782                  scoped_ptr_sfree stringGuard($1);
783                  set($$, SelectionParserValue::createString($1));
784                  END_ACTION;
785              }
786            | value_item_range    { $$ = $1; }
787 ;
788
789 value_item_range:
790              integer_number TO integer_number
791              {
792                  BEGIN_ACTION;
793                  set($$, SelectionParserValue::createIntegerRange($1, $3));
794                  END_ACTION;
795              }
796            | integer_number TO real_number
797              {
798                  BEGIN_ACTION;
799                  set($$, SelectionParserValue::createRealRange($1, $3));
800                  END_ACTION;
801              }
802            | real_number TO number
803              {
804                  BEGIN_ACTION;
805                  set($$, SelectionParserValue::createRealRange($1, $3));
806                  END_ACTION;
807              }
808 ;