Use flex for generating the scanner, add support for parsing from strings
[platform/upstream/libxkbcommon.git] / src / xkbcomp / xkbparse.y
1 /************************************************************
2  Copyright (c) 1994 by Silicon Graphics Computer Systems, Inc.
3
4  Permission to use, copy, modify, and distribute this
5  software and its documentation for any purpose and without
6  fee is hereby granted, provided that the above copyright
7  notice appear in all copies and that both that copyright
8  notice and this permission notice appear in supporting
9  documentation, and that the name of Silicon Graphics not be
10  used in advertising or publicity pertaining to distribution
11  of the software without specific prior written permission.
12  Silicon Graphics makes no representation about the suitability
13  of this software for any purpose. It is provided "as is"
14  without any express or implied warranty.
15
16  SILICON GRAPHICS DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS
17  SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
18  AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL SILICON
19  GRAPHICS BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
20  DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
21  DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
22  OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION  WITH
23  THE USE OR PERFORMANCE OF THIS SOFTWARE.
24
25  ********************************************************/
26
27 %token
28         END_OF_FILE     0
29         ERROR_TOK       255
30         XKB_KEYMAP      1
31         XKB_KEYCODES    2
32         XKB_TYPES       3
33         XKB_SYMBOLS     4
34         XKB_COMPATMAP   5
35         XKB_GEOMETRY    6
36         XKB_SEMANTICS   7
37         XKB_LAYOUT      8
38         INCLUDE         10
39         OVERRIDE        11
40         AUGMENT         12
41         REPLACE         13
42         ALTERNATE       14
43         VIRTUAL_MODS    20
44         TYPE            21
45         INTERPRET       22
46         ACTION_TOK      23
47         KEY             24
48         ALIAS           25
49         GROUP           26
50         MODIFIER_MAP    27
51         INDICATOR       28
52         SHAPE           29
53         KEYS            30
54         ROW             31
55         SECTION         32
56         OVERLAY         33
57         TEXT            34
58         OUTLINE         35
59         SOLID           36
60         LOGO            37
61         VIRTUAL         38
62         EQUALS          40
63         PLUS            41
64         MINUS           42
65         DIVIDE          43
66         TIMES           44
67         OBRACE          45
68         CBRACE          46
69         OPAREN          47
70         CPAREN          48
71         OBRACKET        49
72         CBRACKET        50
73         DOT             51
74         COMMA           52
75         SEMI            53
76         EXCLAM          54
77         INVERT          55
78         STRING          60
79         INTEGER         61
80         FLOAT           62
81         IDENT           63
82         KEYNAME         64
83         PARTIAL         70
84         DEFAULT         71
85         HIDDEN          72
86         ALPHANUMERIC_KEYS       73
87         MODIFIER_KEYS           74
88         KEYPAD_KEYS             75
89         FUNCTION_KEYS           76
90         ALTERNATE_GROUP         77
91 %{
92 #define DEBUG 1
93 #ifdef DEBUG
94 #define YYDEBUG 1
95 #endif
96 #include "parseutils.h"
97 #include "xkbmisc.h"
98 #include <X11/Xlib.h>
99 #include <X11/keysym.h>
100 #include <stdlib.h>
101
102 %}
103 %right  EQUALS
104 %left   PLUS MINUS
105 %left   TIMES DIVIDE
106 %left   EXCLAM INVERT
107 %left   OPAREN
108 %start  XkbFile
109 %union  {
110         int              ival;
111         unsigned         uval;
112         char            *str;
113         Atom            sval;
114         ParseCommon     *any;
115         ExprDef         *expr;
116         VarDef          *var;
117         VModDef         *vmod;
118         InterpDef       *interp;
119         KeyTypeDef      *keyType;
120         SymbolsDef      *syms;
121         ModMapDef       *modMask;
122         GroupCompatDef  *groupCompat;
123         IndicatorMapDef *ledMap;
124         IndicatorNameDef *ledName;
125         KeycodeDef      *keyName;
126         KeyAliasDef     *keyAlias;
127         ShapeDef        *shape;
128         SectionDef      *section;
129         RowDef          *row;
130         KeyDef          *key;
131         OverlayDef      *overlay;
132         OverlayKeyDef   *olKey;
133         OutlineDef      *outline;
134         DoodadDef       *doodad;
135         XkbFile         *file;
136 }
137 %type <ival>    Number Integer Float SignedNumber
138 %type <uval>    XkbCompositeType FileType MergeMode OptMergeMode
139 %type <uval>    DoodadType Flag Flags OptFlags
140 %type <str>     KeyName MapName OptMapName KeySym
141 %type <sval>    FieldSpec Ident Element String
142 %type <any>     DeclList Decl
143 %type <expr>    OptExprList ExprList Expr Term Lhs Terminal ArrayInit
144 %type <expr>    OptKeySymList KeySymList Action ActionList Coord CoordList
145 %type <var>     VarDecl VarDeclList SymbolsBody SymbolsVarDecl
146 %type <vmod>    VModDecl VModDefList VModDef
147 %type <interp>  InterpretDecl InterpretMatch
148 %type <keyType> KeyTypeDecl
149 %type <syms>    SymbolsDecl
150 %type <modMask> ModMapDecl
151 %type <groupCompat> GroupCompatDecl
152 %type <ledMap>  IndicatorMapDecl
153 %type <ledName> IndicatorNameDecl
154 %type <keyName> KeyNameDecl
155 %type <keyAlias> KeyAliasDecl
156 %type <shape>   ShapeDecl
157 %type <section> SectionDecl
158 %type <row>     SectionBody SectionBodyItem
159 %type <key>     RowBody RowBodyItem Keys Key
160 %type <overlay> OverlayDecl
161 %type <olKey>   OverlayKeyList OverlayKey
162 %type <outline> OutlineList OutlineInList
163 %type <doodad>  DoodadDecl
164 %type <file>    XkbFile XkbMapConfigList XkbMapConfig XkbConfig
165 %type <file>    XkbCompositeMap XkbCompMapList
166 %%
167 XkbFile         :       XkbCompMapList
168                         { $$= rtrnValue= $1; }
169                 |       XkbMapConfigList
170                         { $$= rtrnValue= $1;  }
171                 |       XkbConfig
172                         { $$= rtrnValue= $1; }
173                 ;
174
175 XkbCompMapList  :       XkbCompMapList XkbCompositeMap
176                         { $$= (XkbFile *)AppendStmt(&$1->common,&$2->common); }
177                 |       XkbCompositeMap
178                         { $$= $1; }
179                 ;
180
181 XkbCompositeMap :       OptFlags XkbCompositeType OptMapName OBRACE
182                             XkbMapConfigList
183                         CBRACE SEMI
184                         { $$= CreateXKBFile($2,$3,&$5->common,$1); }
185                 ;
186
187 XkbCompositeType:       XKB_KEYMAP      { $$= XkmKeymapFile; }
188                 |       XKB_SEMANTICS   { $$= XkmSemanticsFile; }
189                 |       XKB_LAYOUT      { $$= XkmLayoutFile; }
190                 ;
191
192 XkbMapConfigList :      XkbMapConfigList XkbMapConfig
193                         { $$= (XkbFile *)AppendStmt(&$1->common,&$2->common); }
194                 |       XkbMapConfig
195                         { $$= $1; }
196                 ;
197
198 XkbMapConfig    :       OptFlags FileType OptMapName OBRACE
199                             DeclList
200                         CBRACE SEMI
201                         { $$= CreateXKBFile($2,$3,$5,$1); }
202                 ;
203
204 XkbConfig       :       OptFlags FileType OptMapName DeclList
205                         { $$= CreateXKBFile($2,$3,$4,$1); }
206                 ;
207
208
209 FileType        :       XKB_KEYCODES            { $$= XkmKeyNamesIndex; }
210                 |       XKB_TYPES               { $$= XkmTypesIndex; }
211                 |       XKB_COMPATMAP           { $$= XkmCompatMapIndex; }
212                 |       XKB_SYMBOLS             { $$= XkmSymbolsIndex; }
213                 |       XKB_GEOMETRY            { $$= XkmGeometryIndex; }
214                 ;
215
216 OptFlags        :       Flags                   { $$= $1; }
217                 |                               { $$= 0; }
218                 ;
219
220 Flags           :       Flags Flag              { $$= (($1)|($2)); }
221                 |       Flag                    { $$= $1; }
222                 ;
223
224 Flag            :       PARTIAL                 { $$= XkbLC_Partial; }
225                 |       DEFAULT                 { $$= XkbLC_Default; }
226                 |       HIDDEN                  { $$= XkbLC_Hidden; }
227                 |       ALPHANUMERIC_KEYS       { $$= XkbLC_AlphanumericKeys; }
228                 |       MODIFIER_KEYS           { $$= XkbLC_ModifierKeys; }
229                 |       KEYPAD_KEYS             { $$= XkbLC_KeypadKeys; }
230                 |       FUNCTION_KEYS           { $$= XkbLC_FunctionKeys; }
231                 |       ALTERNATE_GROUP         { $$= XkbLC_AlternateGroup; }
232                 ;
233
234 DeclList        :       DeclList Decl
235                         { $$= AppendStmt($1,$2); }
236                 |       { $$= NULL; }
237                 ;
238
239 Decl            :       OptMergeMode VarDecl
240                         {
241                             $2->merge= StmtSetMerge(&$2->common,$1);
242                             $$= &$2->common;
243                         }
244                 |       OptMergeMode VModDecl
245                         {
246                             $2->merge= StmtSetMerge(&$2->common,$1);
247                             $$= &$2->common;
248                         }
249                 |       OptMergeMode InterpretDecl
250                         {
251                             $2->merge= StmtSetMerge(&$2->common,$1);
252                             $$= &$2->common;
253                         }
254                 |       OptMergeMode KeyNameDecl
255                         {
256                             $2->merge= StmtSetMerge(&$2->common,$1);
257                             $$= &$2->common;
258                         }
259                 |       OptMergeMode KeyAliasDecl
260                         {
261                             $2->merge= StmtSetMerge(&$2->common,$1);
262                             $$= &$2->common;
263                         }
264                 |       OptMergeMode KeyTypeDecl
265                         {
266                             $2->merge= StmtSetMerge(&$2->common,$1);
267                             $$= &$2->common;
268                         }
269                 |       OptMergeMode SymbolsDecl
270                         {
271                             $2->merge= StmtSetMerge(&$2->common,$1);
272                             $$= &$2->common;
273                         }
274                 |       OptMergeMode ModMapDecl
275                         {
276                             $2->merge= StmtSetMerge(&$2->common,$1);
277                             $$= &$2->common;
278                         }
279                 |       OptMergeMode GroupCompatDecl
280                         {
281                             $2->merge= StmtSetMerge(&$2->common,$1);
282                             $$= &$2->common;
283                         }
284                 |       OptMergeMode IndicatorMapDecl
285                         {
286                             $2->merge= StmtSetMerge(&$2->common,$1);
287                             $$= &$2->common;
288                         }
289                 |       OptMergeMode IndicatorNameDecl
290                         {
291                             $2->merge= StmtSetMerge(&$2->common,$1);
292                             $$= &$2->common;
293                         }
294                 |       OptMergeMode ShapeDecl
295                         {
296                             $2->merge= StmtSetMerge(&$2->common,$1);
297                             $$= &$2->common;
298                         }
299                 |       OptMergeMode SectionDecl
300                         {
301                             $2->merge= StmtSetMerge(&$2->common,$1);
302                             $$= &$2->common;
303                         }
304                 |       OptMergeMode DoodadDecl
305                         {
306                             $2->merge= StmtSetMerge(&$2->common,$1);
307                             $$= &$2->common;
308                         }
309                 |       MergeMode STRING
310                         {
311                             if ($1==MergeAltForm) {
312                                 yyerror("cannot use 'alternate' to include other maps");
313                                 $$= &IncludeCreate(scanBuf,MergeDefault)->common;
314                             }
315                             else {
316                                 $$= &IncludeCreate(scanBuf,$1)->common;
317                             }
318                         }
319                 ;
320
321 VarDecl         :       Lhs EQUALS Expr SEMI
322                         { $$= VarCreate($1,$3); }
323                 |       Ident SEMI
324                         { $$= BoolVarCreate($1,1); }
325                 |       EXCLAM Ident SEMI
326                         { $$= BoolVarCreate($2,0); }
327                 ;
328
329 KeyNameDecl     :       KeyName EQUALS Expr SEMI
330                         {
331                             KeycodeDef *def;
332
333                             def= KeycodeCreate($1,$3);
334                             if ($1)
335                                 free($1);
336                             $$= def;
337                         }
338                 ;
339
340 KeyAliasDecl    :       ALIAS KeyName EQUALS KeyName SEMI
341                         {
342                             KeyAliasDef *def;
343                             def= KeyAliasCreate($2,$4);
344                             if ($2)     free($2);       
345                             if ($4)     free($4);       
346                             $$= def;
347                         }
348                 ;
349
350 VModDecl        :       VIRTUAL_MODS VModDefList SEMI
351                         { $$= $2; }
352                 ;
353
354 VModDefList     :       VModDefList COMMA VModDef
355                         { $$= (VModDef *)AppendStmt(&$1->common,&$3->common); }
356                 |       VModDef
357                         { $$= $1; }
358                 ;
359
360 VModDef         :       Ident
361                         { $$= VModCreate($1,NULL); }
362                 |       Ident EQUALS Expr
363                         { $$= VModCreate($1,$3); }
364                 ;
365
366 InterpretDecl   :       INTERPRET InterpretMatch OBRACE
367                             VarDeclList
368                         CBRACE SEMI
369                         {
370                             $2->def= $4;
371                             $$= $2;
372                         }
373                 ;
374
375 InterpretMatch  :       KeySym PLUS Expr        
376                         { $$= InterpCreate($1, $3); }
377                 |       KeySym                  
378                         { $$= InterpCreate($1, NULL); }
379                 ;
380
381 VarDeclList     :       VarDeclList VarDecl
382                         { $$= (VarDef *)AppendStmt(&$1->common,&$2->common); }
383                 |       VarDecl
384                         { $$= $1; }
385                 ;
386
387 KeyTypeDecl     :       TYPE String OBRACE
388                             VarDeclList
389                         CBRACE SEMI
390                         { $$= KeyTypeCreate($2,$4); }
391                 ;
392
393 SymbolsDecl     :       KEY KeyName OBRACE
394                             SymbolsBody
395                         CBRACE SEMI
396                         { $$= SymbolsCreate($2,(ExprDef *)$4); }
397                 ;
398
399 SymbolsBody     :       SymbolsBody COMMA SymbolsVarDecl
400                         { $$= (VarDef *)AppendStmt(&$1->common,&$3->common); }
401                 |       SymbolsVarDecl
402                         { $$= $1; }
403                 |       { $$= NULL; }
404                 ;
405
406 SymbolsVarDecl  :       Lhs EQUALS Expr
407                         { $$= VarCreate($1,$3); }
408                 |       Lhs EQUALS ArrayInit
409                         { $$= VarCreate($1,$3); }
410                 |       Ident
411                         { $$= BoolVarCreate($1,1); }
412                 |       EXCLAM Ident
413                         { $$= BoolVarCreate($2,0); }
414                 |       ArrayInit
415                         { $$= VarCreate(NULL,$1); }
416                 ;
417
418 ArrayInit       :       OBRACKET OptKeySymList CBRACKET
419                         { $$= $2; }
420                 |       OBRACKET ActionList CBRACKET
421                         { $$= ExprCreateUnary(ExprActionList,TypeAction,$2); }
422                 ;
423
424 GroupCompatDecl :       GROUP Integer EQUALS Expr SEMI
425                         { $$= GroupCompatCreate($2,$4); }
426                 ;
427
428 ModMapDecl      :       MODIFIER_MAP Ident OBRACE ExprList CBRACE SEMI
429                         { $$= ModMapCreate($2,$4); }
430                 ;
431
432 IndicatorMapDecl:       INDICATOR String OBRACE VarDeclList CBRACE SEMI
433                         { $$= IndicatorMapCreate($2,$4); }
434                 ;
435
436 IndicatorNameDecl:      INDICATOR Integer EQUALS Expr SEMI
437                         { $$= IndicatorNameCreate($2,$4,False); }
438                 |       VIRTUAL INDICATOR Integer EQUALS Expr SEMI
439                         { $$= IndicatorNameCreate($3,$5,True); }
440                 ;
441
442 ShapeDecl       :       SHAPE String OBRACE OutlineList CBRACE SEMI
443                         { $$= ShapeDeclCreate($2,(OutlineDef *)&$4->common); }
444                 |       SHAPE String OBRACE CoordList CBRACE SEMI
445                         {
446                             OutlineDef *outlines;
447                             outlines= OutlineCreate(None,$4);
448                             $$= ShapeDeclCreate($2,outlines);
449                         }
450                 ;
451
452 SectionDecl     :       SECTION String OBRACE SectionBody CBRACE SEMI
453                         { $$= SectionDeclCreate($2,$4); }
454                 ;
455
456 SectionBody     :       SectionBody SectionBodyItem
457                         { $$=(RowDef *)AppendStmt(&$1->common,&$2->common);}
458                 |       SectionBodyItem
459                         { $$= $1; }
460                 ;
461
462 SectionBodyItem :       ROW OBRACE RowBody CBRACE SEMI
463                         { $$= RowDeclCreate($3); }
464                 |       VarDecl
465                         { $$= (RowDef *)$1; }
466                 |       DoodadDecl
467                         { $$= (RowDef *)$1; }
468                 |       IndicatorMapDecl
469                         { $$= (RowDef *)$1; }
470                 |       OverlayDecl
471                         { $$= (RowDef *)$1; }
472                 ;
473
474 RowBody         :       RowBody RowBodyItem
475                         { $$=(KeyDef *)AppendStmt(&$1->common,&$2->common);}
476                 |       RowBodyItem
477                         { $$= $1; }
478                 ;
479
480 RowBodyItem     :       KEYS OBRACE Keys CBRACE SEMI
481                         { $$= $3; }
482                 |       VarDecl
483                         { $$= (KeyDef *)$1; }
484                 ;
485
486 Keys            :       Keys COMMA Key
487                         { $$=(KeyDef *)AppendStmt(&$1->common,&$3->common);}
488                 |       Key
489                         { $$= $1; }
490                 ;
491
492 Key             :       KeyName
493                         { $$= KeyDeclCreate($1,NULL); }
494                 |       OBRACE ExprList CBRACE
495                         { $$= KeyDeclCreate(NULL,$2); }
496                 ;
497
498 OverlayDecl     :       OVERLAY String OBRACE OverlayKeyList CBRACE SEMI
499                         { $$= OverlayDeclCreate($2,$4); }
500                 ;
501
502 OverlayKeyList  :       OverlayKeyList COMMA OverlayKey
503                         {
504                             $$= (OverlayKeyDef *)
505                                 AppendStmt(&$1->common,&$3->common);
506                         }
507                 |       OverlayKey
508                         { $$= $1; }
509                 ;
510
511 OverlayKey      :       KeyName EQUALS KeyName
512                         { $$= OverlayKeyCreate($1,$3); }
513                 ;
514
515 OutlineList     :       OutlineList COMMA OutlineInList
516                         { $$=(OutlineDef *)AppendStmt(&$1->common,&$3->common);}
517                 |       OutlineInList
518                         { $$= $1; }
519                 ;
520
521 OutlineInList   :       OBRACE CoordList CBRACE
522                         { $$= OutlineCreate(None,$2); }
523                 |       Ident EQUALS OBRACE CoordList CBRACE
524                         { $$= OutlineCreate($1,$4); }
525                 |       Ident EQUALS Expr
526                         { $$= OutlineCreate($1,$3); }
527                 ;
528
529 CoordList       :       CoordList COMMA Coord
530                         { $$= (ExprDef *)AppendStmt(&$1->common,&$3->common); }
531                 |       Coord
532                         { $$= $1; }
533                 ;
534
535 Coord           :       OBRACKET SignedNumber COMMA SignedNumber CBRACKET
536                         {
537                             ExprDef *expr;
538                             expr= ExprCreate(ExprCoord,TypeUnknown);
539                             expr->value.coord.x= $2;
540                             expr->value.coord.y= $4;
541                             $$= expr;
542                         }
543                 ;
544
545 DoodadDecl      :       DoodadType String OBRACE VarDeclList CBRACE SEMI
546                         { $$= DoodadCreate($1,$2,$4); }
547                 ;
548
549 DoodadType      :       TEXT                    { $$= XkbTextDoodad; }
550                 |       OUTLINE                 { $$= XkbOutlineDoodad; }
551                 |       SOLID                   { $$= XkbSolidDoodad; }
552                 |       LOGO                    { $$= XkbLogoDoodad; }
553                 ;
554
555 FieldSpec       :       Ident                   { $$= $1; }
556                 |       Element                 { $$= $1; }
557                 ;
558
559 Element         :       ACTION_TOK              
560                         { $$= XkbcInternAtom("action",False); }
561                 |       INTERPRET
562                         { $$= XkbcInternAtom("interpret",False); }
563                 |       TYPE
564                         { $$= XkbcInternAtom("type",False); }
565                 |       KEY
566                         { $$= XkbcInternAtom("key",False); }
567                 |       GROUP
568                         { $$= XkbcInternAtom("group",False); }
569                 |       MODIFIER_MAP
570                         {$$=XkbcInternAtom("modifier_map",False);}
571                 |       INDICATOR
572                         { $$= XkbcInternAtom("indicator",False); }
573                 |       SHAPE   
574                         { $$= XkbcInternAtom("shape",False); }
575                 |       ROW     
576                         { $$= XkbcInternAtom("row",False); }
577                 |       SECTION 
578                         { $$= XkbcInternAtom("section",False); }
579                 |       TEXT
580                         { $$= XkbcInternAtom("text",False); }
581                 ;
582
583 OptMergeMode    :       MergeMode               { $$= $1; }
584                 |                               { $$= MergeDefault; }
585                 ;
586
587 MergeMode       :       INCLUDE                 { $$= MergeDefault; }
588                 |       AUGMENT                 { $$= MergeAugment; }
589                 |       OVERRIDE                { $$= MergeOverride; }
590                 |       REPLACE                 { $$= MergeReplace; }
591                 |       ALTERNATE               { $$= MergeAltForm; }
592                 ;
593
594 OptExprList     :       ExprList                        { $$= $1; }
595                 |                               { $$= NULL; }
596                 ;
597
598 ExprList        :       ExprList COMMA Expr
599                         { $$= (ExprDef *)AppendStmt(&$1->common,&$3->common); }
600                 |       Expr
601                         { $$= $1; }
602                 ;
603
604 Expr            :       Expr DIVIDE Expr
605                         { $$= ExprCreateBinary(OpDivide,$1,$3); }
606                 |       Expr PLUS Expr
607                         { $$= ExprCreateBinary(OpAdd,$1,$3); }
608                 |       Expr MINUS Expr
609                         { $$= ExprCreateBinary(OpSubtract,$1,$3); }
610                 |       Expr TIMES Expr
611                         { $$= ExprCreateBinary(OpMultiply,$1,$3); }
612                 |       Lhs EQUALS Expr
613                         { $$= ExprCreateBinary(OpAssign,$1,$3); }
614                 |       Term
615                         { $$= $1; }
616                 ;
617
618 Term            :       MINUS Term
619                         { $$= ExprCreateUnary(OpNegate,$2->type,$2); }
620                 |       PLUS Term
621                         { $$= ExprCreateUnary(OpUnaryPlus,$2->type,$2); }
622                 |       EXCLAM Term
623                         { $$= ExprCreateUnary(OpNot,TypeBoolean,$2); }
624                 |       INVERT Term
625                         { $$= ExprCreateUnary(OpInvert,$2->type,$2); }
626                 |       Lhs
627                         { $$= $1;  }
628                 |       FieldSpec OPAREN OptExprList CPAREN %prec OPAREN
629                         { $$= ActionCreate($1,$3); }
630                 |       Terminal
631                         { $$= $1;  }
632                 |       OPAREN Expr CPAREN
633                         { $$= $2;  }
634                 ;
635
636 ActionList      :       ActionList COMMA Action
637                         { $$= (ExprDef *)AppendStmt(&$1->common,&$3->common); }
638                 |       Action
639                         { $$= $1; }
640                 ;
641
642 Action          :       FieldSpec OPAREN OptExprList CPAREN
643                         { $$= ActionCreate($1,$3); }
644                 ;
645
646 Lhs             :       FieldSpec
647                         {
648                             ExprDef *expr;
649                             expr= ExprCreate(ExprIdent,TypeUnknown);
650                             expr->value.str= $1;
651                             $$= expr;
652                         }
653                 |       FieldSpec DOT FieldSpec
654                         {
655                             ExprDef *expr;
656                             expr= ExprCreate(ExprFieldRef,TypeUnknown);
657                             expr->value.field.element= $1;
658                             expr->value.field.field= $3;
659                             $$= expr;
660                         }
661                 |       FieldSpec OBRACKET Expr CBRACKET
662                         {
663                             ExprDef *expr;
664                             expr= ExprCreate(ExprArrayRef,TypeUnknown);
665                             expr->value.array.element= None;
666                             expr->value.array.field= $1;
667                             expr->value.array.entry= $3;
668                             $$= expr;
669                         }
670                 |       FieldSpec DOT FieldSpec OBRACKET Expr CBRACKET
671                         {
672                             ExprDef *expr;
673                             expr= ExprCreate(ExprArrayRef,TypeUnknown);
674                             expr->value.array.element= $1;
675                             expr->value.array.field= $3;
676                             expr->value.array.entry= $5;
677                             $$= expr;
678                         }
679                 ;
680
681 Terminal        :       String
682                         {
683                             ExprDef *expr;
684                             expr= ExprCreate(ExprValue,TypeString);
685                             expr->value.str= $1;
686                             $$= expr;
687                         }
688                 |       Integer
689                         {
690                             ExprDef *expr;
691                             expr= ExprCreate(ExprValue,TypeInt);
692                             expr->value.ival= $1;
693                             $$= expr;
694                         }
695                 |       Float
696                         {
697                             ExprDef *expr;
698                             expr= ExprCreate(ExprValue,TypeFloat);
699                             expr->value.ival= $1;
700                             $$= expr;
701                         }
702                 |       KeyName
703                         {
704                             ExprDef *expr;
705                             expr= ExprCreate(ExprValue,TypeKeyName);
706                             memset(expr->value.keyName,0,5);
707                             strncpy(expr->value.keyName,$1,4);
708                             free($1);
709                             $$= expr;
710                         }
711                 ;
712
713 OptKeySymList   :       KeySymList                      { $$= $1; }
714                 |                                       { $$= NULL; }
715                 ;
716
717 KeySymList      :       KeySymList COMMA KeySym
718                         { $$= AppendKeysymList($1,$3); }
719                 |       KeySym
720                         { $$= CreateKeysymList($1); }
721                 ;
722
723 KeySym          :       IDENT   { $$= strdup(scanBuf); }
724                 |       SECTION { $$= strdup("section"); }
725                 |       Integer         
726                         {
727                             if ($1 < 10) {      /* XK_0 .. XK_9 */
728                                 $$= malloc(2);
729                                 $$[0]= $1 + '0';
730                                 $$[1]= '\0';
731                             }
732                             else {
733                                 $$= malloc(17);
734                                 snprintf($$, 17, "%x", $1);
735                             }
736                         }
737                 ;
738
739 SignedNumber    :       MINUS Number    { $$= -$2; }
740                 |       Number              { $$= $1; }
741                 ;
742
743 Number          :       FLOAT           { $$= scanInt; }
744                 |       INTEGER         { $$= scanInt*XkbGeomPtsPerMM; }
745                 ;
746
747 Float           :       FLOAT           { $$= scanInt; }
748                 ;
749
750 Integer         :       INTEGER         { $$= scanInt; }
751                 ;
752
753 KeyName         :       KEYNAME         { $$= strdup(scanBuf); }
754                 ;
755
756 Ident           :       IDENT   { $$= XkbcInternAtom(scanBuf,False); }
757                 |       DEFAULT { $$= XkbcInternAtom("default",False); }
758                 ;
759
760 String          :       STRING  { $$= XkbcInternAtom(scanBuf,False); }
761                 ;
762
763 OptMapName      :       MapName { $$= $1; }
764                 |               { $$= NULL; }
765                 ;
766
767 MapName         :       STRING  { $$= strdup(scanBuf); }
768                 ;