1 %{ /* rcparse.y -- parser for Windows rc files
2 Copyright 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2005, 2007
3 Free Software Foundation, Inc.
4 Written by Ian Lance Taylor, Cygnus Support.
5 Extended by Kai Tietz, Onevision.
7 This file is part of GNU Binutils.
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, write to the Free Software
21 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA
24 /* This is a parser for Windows rc files. It is based on the parser
25 by Gunther Ebert <gunther.ebert@ixos-leipzig.de>. */
30 #include "libiberty.h"
32 #include "safe-ctype.h"
34 /* The current language. */
36 static unsigned short language;
38 /* The resource information during a sub statement. */
40 static rc_res_res_info sub_res_info;
42 /* Dialog information. This is built by the nonterminals styles and
45 static rc_dialog dialog;
47 /* This is used when building a style. It is modified by the
48 nonterminal styleexpr. */
50 static unsigned long style;
52 /* These are used when building a control. They are set before using
55 static rc_uint_type base_style;
56 static rc_uint_type default_style;
57 static rc_res_id class;
58 static rc_res_id res_text_field;
59 static unichar null_unichar;
61 /* This is used for COMBOBOX, LISTBOX and EDITTEXT which
62 do not allow resource 'text' field in control definition. */
63 static const rc_res_id res_null_text = { 1, {{0, &null_unichar}}};
71 rc_dialog_control *dialog_control;
72 rc_menuitem *menuitem;
75 rc_rcdata_item *first;
78 rc_rcdata_item *rcdata_item;
79 rc_fixed_versioninfo *fixver;
81 rc_ver_stringinfo *verstring;
82 rc_ver_varinfo *vervar;
83 rc_toolbar_item *toobar_item;
85 rc_res_res_info res_info;
94 /* Nonzero if this number was explicitly specified as long. */
114 %token ACCELERATORS VIRTKEY ASCII NOINVERT SHIFT CONTROL ALT
117 %token DIALOG DIALOGEX EXSTYLE CAPTION CLASS STYLE
118 %token AUTO3STATE AUTOCHECKBOX AUTORADIOBUTTON CHECKBOX COMBOBOX CTEXT
119 %token DEFPUSHBUTTON EDITTEXT GROUPBOX LISTBOX LTEXT PUSHBOX PUSHBUTTON
120 %token RADIOBUTTON RTEXT SCROLLBAR STATE3 USERBUTTON
121 %token BEDIT HEDIT IEDIT
124 %token ANICURSOR ANIICON DLGINCLUDE DLGINIT FONTDIR HTML MANIFEST PLUGPLAY VXD TOOLBAR BUTTON
125 %token LANGUAGE CHARACTERISTICS VERSIONK
126 %token MENU MENUEX MENUITEM SEPARATOR POPUP CHECKED GRAYED HELP INACTIVE
127 %token MENUBARBREAK MENUBREAK
131 %token VERSIONINFO FILEVERSION PRODUCTVERSION FILEFLAGSMASK FILEFLAGS
132 %token FILEOS FILETYPE FILESUBTYPE BLOCKSTRINGFILEINFO BLOCKVARFILEINFO
135 %token MOVEABLE FIXED PURE IMPURE PRELOAD LOADONCALL DISCARDABLE
137 %token <uni> QUOTEDUNISTRING
138 %token <s> QUOTEDSTRING STRING
140 %token <suni> SIZEDUNISTRING
141 %token <ss> SIZEDSTRING
144 %type <pacc> acc_entries
145 %type <acc> acc_entry acc_event
146 %type <dialog_control> control control_params
147 %type <menuitem> menuitems menuitem menuexitems menuexitem
148 %type <rcdata> optrcdata_data optrcdata_data_int rcdata_data
149 %type <rcdata_item> opt_control_data
150 %type <fixver> fixedverinfo
151 %type <verinfo> verblocks
152 %type <verstring> vervals
153 %type <vervar> vertrans
154 %type <toobar_item> toolbar_data
155 %type <res_info> suboptions memflags_move_discard memflags_move
156 %type <memflags> memflag
157 %type <id> id rcdata_id optresidc resref resid cresid
158 %type <il> exstyle parennumber
159 %type <il> numexpr posnumexpr cnumexpr optcnumexpr cposnumexpr
160 %type <is> acc_options acc_option menuitem_flags menuitem_flag
162 %type <uni> res_unicode_string resname
163 %type <ss> sizedstring
164 %type <suni> sizedunistring
165 %type <i> sizednumexpr sizedposnumexpr
192 | input IGNORED_TOKEN
195 /* Accelerator resources. */
198 id ACCELERATORS suboptions BEG acc_entries END
200 define_accelerator ($1, &$3, $5);
201 if (yychar != YYEMPTY)
203 rcparse_discard_strings ();
212 | acc_entries acc_entry
216 a = (rc_accelerator *) res_alloc (sizeof *a);
224 for (pp = &$1->next; *pp != NULL; pp = &(*pp)->next)
233 acc_event cposnumexpr
238 | acc_event cposnumexpr ',' acc_options
243 if (($$.flags & ACC_VIRTKEY) == 0
244 && ($$.flags & (ACC_SHIFT | ACC_CONTROL)) != 0)
245 rcparse_warning (_("inappropriate modifiers for non-VIRTKEY"));
262 $$.flags = ACC_CONTROL | ACC_VIRTKEY;
268 rcparse_warning (_("accelerator should only be one character"));
284 | acc_options ',' acc_option
288 /* I've had one report that the comma is optional. */
289 | acc_options acc_option
302 /* This is just the absence of VIRTKEY. */
323 /* Bitmap resources. */
326 id BITMAP memflags_move file_name
328 define_bitmap ($1, &$3, $4);
329 if (yychar != YYEMPTY)
331 rcparse_discard_strings ();
335 /* Cursor resources. */
338 id CURSOR memflags_move_discard file_name
340 define_cursor ($1, &$3, $4);
341 if (yychar != YYEMPTY)
343 rcparse_discard_strings ();
347 /* Dialog resources. */
350 id DIALOG memflags_move exstyle posnumexpr cnumexpr cnumexpr
353 memset (&dialog, 0, sizeof dialog);
358 dialog.style = WS_POPUP | WS_BORDER | WS_SYSMENU;
360 dialog.menu.named = 1;
361 dialog.class.named = 1;
364 dialog.controls = NULL;
368 styles BEG controls END
370 define_dialog ($1, &sub_res_info, &dialog);
371 if (yychar != YYEMPTY)
373 rcparse_discard_strings ();
375 | id DIALOGEX memflags_move exstyle posnumexpr cnumexpr cnumexpr
378 memset (&dialog, 0, sizeof dialog);
383 dialog.style = WS_POPUP | WS_BORDER | WS_SYSMENU;
385 dialog.menu.named = 1;
386 dialog.class.named = 1;
388 dialog.ex = ((rc_dialog_ex *)
389 res_alloc (sizeof (rc_dialog_ex)));
390 memset (dialog.ex, 0, sizeof (rc_dialog_ex));
391 dialog.controls = NULL;
395 styles BEG controls END
397 define_dialog ($1, &sub_res_info, &dialog);
398 if (yychar != YYEMPTY)
400 rcparse_discard_strings ();
402 | id DIALOGEX memflags_move exstyle posnumexpr cnumexpr cnumexpr
405 memset (&dialog, 0, sizeof dialog);
410 dialog.style = WS_POPUP | WS_BORDER | WS_SYSMENU;
412 dialog.menu.named = 1;
413 dialog.class.named = 1;
415 dialog.ex = ((rc_dialog_ex *)
416 res_alloc (sizeof (rc_dialog_ex)));
417 memset (dialog.ex, 0, sizeof (rc_dialog_ex));
418 dialog.ex->help = $9;
419 dialog.controls = NULL;
423 styles BEG controls END
425 define_dialog ($1, &sub_res_info, &dialog);
426 if (yychar != YYEMPTY)
428 rcparse_discard_strings ();
437 | EXSTYLE '=' numexpr
445 | styles CAPTION res_unicode_string
447 dialog.style |= WS_CAPTION;
458 dialog.style = style;
460 | styles EXSTYLE numexpr
464 | styles CLASS res_unicode_string
466 res_unistring_to_id (& dialog.class, $3);
468 | styles FONT numexpr ',' res_unicode_string
470 dialog.style |= DS_SETFONT;
472 dialog.pointsize = $3;
474 if (dialog.ex != NULL)
476 dialog.ex->weight = 0;
477 dialog.ex->italic = 0;
478 dialog.ex->charset = 1;
481 | styles FONT numexpr ',' res_unicode_string cnumexpr
483 dialog.style |= DS_SETFONT;
485 dialog.pointsize = $3;
487 if (dialog.ex == NULL)
488 rcparse_warning (_("extended FONT requires DIALOGEX"));
491 dialog.ex->weight = $6;
492 dialog.ex->italic = 0;
493 dialog.ex->charset = 1;
496 | styles FONT numexpr ',' res_unicode_string cnumexpr cnumexpr
498 dialog.style |= DS_SETFONT;
500 dialog.pointsize = $3;
502 if (dialog.ex == NULL)
503 rcparse_warning (_("extended FONT requires DIALOGEX"));
506 dialog.ex->weight = $6;
507 dialog.ex->italic = $7;
508 dialog.ex->charset = 1;
511 | styles FONT numexpr ',' res_unicode_string cnumexpr cnumexpr cnumexpr
513 dialog.style |= DS_SETFONT;
515 dialog.pointsize = $3;
517 if (dialog.ex == NULL)
518 rcparse_warning (_("extended FONT requires DIALOGEX"));
521 dialog.ex->weight = $6;
522 dialog.ex->italic = $7;
523 dialog.ex->charset = $8;
530 | styles CHARACTERISTICS numexpr
532 sub_res_info.characteristics = $3;
534 | styles LANGUAGE numexpr cnumexpr
536 sub_res_info.language = $3 | ($4 << SUBLANG_SHIFT);
538 | styles VERSIONK numexpr
540 sub_res_info.version = $3;
548 rc_dialog_control **pp;
550 for (pp = &dialog.controls; *pp != NULL; pp = &(*pp)->next)
559 default_style = BS_AUTO3STATE | WS_TABSTOP;
560 base_style = BS_AUTO3STATE;
562 class.u.id = CTL_BUTTON;
569 | AUTOCHECKBOX optresidc
571 default_style = BS_AUTOCHECKBOX | WS_TABSTOP;
572 base_style = BS_AUTOCHECKBOX;
574 class.u.id = CTL_BUTTON;
581 | AUTORADIOBUTTON optresidc
583 default_style = BS_AUTORADIOBUTTON | WS_TABSTOP;
584 base_style = BS_AUTORADIOBUTTON;
586 class.u.id = CTL_BUTTON;
595 default_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
596 base_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
598 class.u.id = CTL_EDIT;
604 if (dialog.ex == NULL)
605 rcparse_warning (_("BEDIT requires DIALOGEX"));
606 res_string_to_id (&$$->class, "BEDIT");
610 default_style = BS_CHECKBOX | WS_TABSTOP;
611 base_style = BS_CHECKBOX | WS_TABSTOP;
613 class.u.id = CTL_BUTTON;
622 /* This is as per MSDN documentation. With some (???)
623 versions of MS rc.exe their is no default style. */
624 default_style = CBS_SIMPLE | WS_TABSTOP;
627 class.u.id = CTL_COMBOBOX;
628 res_text_field = res_null_text;
634 | CONTROL optresidc numexpr cresid control_styleexpr cnumexpr
635 cnumexpr cnumexpr cnumexpr optcnumexpr opt_control_data
637 $$ = define_control ($2, $3, $6, $7, $8, $9, $4, style, $10);
640 if (dialog.ex == NULL)
641 rcparse_warning (_("control data requires DIALOGEX"));
645 | CONTROL optresidc numexpr cresid control_styleexpr cnumexpr
646 cnumexpr cnumexpr cnumexpr cnumexpr cnumexpr opt_control_data
648 $$ = define_control ($2, $3, $6, $7, $8, $9, $4, style, $10);
649 if (dialog.ex == NULL)
650 rcparse_warning (_("help ID requires DIALOGEX"));
656 default_style = SS_CENTER | WS_GROUP;
657 base_style = SS_CENTER;
659 class.u.id = CTL_STATIC;
666 | DEFPUSHBUTTON optresidc
668 default_style = BS_DEFPUSHBUTTON | WS_TABSTOP;
669 base_style = BS_DEFPUSHBUTTON | WS_TABSTOP;
671 class.u.id = CTL_BUTTON;
680 default_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
681 base_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
683 class.u.id = CTL_EDIT;
684 res_text_field = res_null_text;
692 default_style = BS_GROUPBOX;
693 base_style = BS_GROUPBOX;
695 class.u.id = CTL_BUTTON;
704 default_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
705 base_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
707 class.u.id = CTL_EDIT;
713 if (dialog.ex == NULL)
714 rcparse_warning (_("IEDIT requires DIALOGEX"));
715 res_string_to_id (&$$->class, "HEDIT");
717 | ICON resref numexpr cnumexpr cnumexpr opt_control_data
719 $$ = define_icon_control ($2, $3, $4, $5, 0, 0, 0, $6,
722 | ICON resref numexpr cnumexpr cnumexpr cnumexpr cnumexpr
725 $$ = define_icon_control ($2, $3, $4, $5, 0, 0, 0, $8,
728 | ICON resref numexpr cnumexpr cnumexpr cnumexpr cnumexpr
729 icon_styleexpr optcnumexpr opt_control_data
731 $$ = define_icon_control ($2, $3, $4, $5, style, $9, 0, $10,
734 | ICON resref numexpr cnumexpr cnumexpr cnumexpr cnumexpr
735 icon_styleexpr cnumexpr cnumexpr opt_control_data
737 $$ = define_icon_control ($2, $3, $4, $5, style, $9, $10, $11,
742 default_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
743 base_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
745 class.u.id = CTL_EDIT;
751 if (dialog.ex == NULL)
752 rcparse_warning (_("IEDIT requires DIALOGEX"));
753 res_string_to_id (&$$->class, "IEDIT");
757 default_style = LBS_NOTIFY | WS_BORDER;
758 base_style = LBS_NOTIFY | WS_BORDER;
760 class.u.id = CTL_LISTBOX;
761 res_text_field = res_null_text;
769 default_style = SS_LEFT | WS_GROUP;
770 base_style = SS_LEFT;
772 class.u.id = CTL_STATIC;
781 default_style = BS_PUSHBOX | WS_TABSTOP;
782 base_style = BS_PUSHBOX;
784 class.u.id = CTL_BUTTON;
790 | PUSHBUTTON optresidc
792 default_style = BS_PUSHBUTTON | WS_TABSTOP;
793 base_style = BS_PUSHBUTTON | WS_TABSTOP;
795 class.u.id = CTL_BUTTON;
802 | RADIOBUTTON optresidc
804 default_style = BS_RADIOBUTTON | WS_TABSTOP;
805 base_style = BS_RADIOBUTTON;
807 class.u.id = CTL_BUTTON;
816 default_style = SS_RIGHT | WS_GROUP;
817 base_style = SS_RIGHT;
819 class.u.id = CTL_STATIC;
828 default_style = SBS_HORZ;
831 class.u.id = CTL_SCROLLBAR;
832 res_text_field = res_null_text;
840 default_style = BS_3STATE | WS_TABSTOP;
841 base_style = BS_3STATE;
843 class.u.id = CTL_BUTTON;
850 | USERBUTTON resref numexpr ',' numexpr ',' numexpr ','
851 numexpr ',' numexpr ','
852 { style = WS_CHILD | WS_VISIBLE; }
853 styleexpr optcnumexpr
857 cid.u.id = CTL_BUTTON;
858 $$ = define_control ($2, $3, $5, $7, $9, $11, cid,
863 /* Parameters for a control. The static variables DEFAULT_STYLE,
864 BASE_STYLE, and CLASS must be initialized before this nonterminal
865 is used. DEFAULT_STYLE is the style to use if no style expression
866 is specified. BASE_STYLE is the base style to use if a style
867 expression is specified; the style expression modifies the base
868 style. CLASS is the class of the control. */
871 numexpr cnumexpr cnumexpr cnumexpr cnumexpr opt_control_data
873 $$ = define_control (res_text_field, $1, $2, $3, $4, $5, class,
874 default_style | WS_CHILD | WS_VISIBLE, 0);
877 if (dialog.ex == NULL)
878 rcparse_warning (_("control data requires DIALOGEX"));
882 | numexpr cnumexpr cnumexpr cnumexpr cnumexpr
883 control_params_styleexpr optcnumexpr opt_control_data
885 $$ = define_control (res_text_field, $1, $2, $3, $4, $5, class, style, $7);
888 if (dialog.ex == NULL)
889 rcparse_warning (_("control data requires DIALOGEX"));
893 | numexpr cnumexpr cnumexpr cnumexpr cnumexpr
894 control_params_styleexpr cnumexpr cnumexpr opt_control_data
896 $$ = define_control (res_text_field, $1, $2, $3, $4, $5, class, style, $7);
897 if (dialog.ex == NULL)
898 rcparse_warning (_("help ID requires DIALOGEX"));
908 res_unistring_to_id (&$$, $2.u.n.name);
917 res_string_to_id (&$$, "");
919 | resid ',' { $$=$1; }
932 $$.u.n.length = unichar_len ($1);
941 | BEG optrcdata_data END
947 /* These only exist to parse a reduction out of a common case. */
951 { style = WS_CHILD | WS_VISIBLE; }
957 { style = SS_ICON | WS_CHILD | WS_VISIBLE; }
961 control_params_styleexpr:
963 { style = base_style | WS_CHILD | WS_VISIBLE; }
967 /* Font resources. */
970 id FONT memflags_move_discard file_name
972 define_font ($1, &$3, $4);
973 if (yychar != YYEMPTY)
975 rcparse_discard_strings ();
979 /* Icon resources. */
982 id ICON memflags_move_discard file_name
984 define_icon ($1, &$3, $4);
985 if (yychar != YYEMPTY)
987 rcparse_discard_strings ();
991 /* Language command. This changes the static variable language, which
992 affects all subsequent resources. */
995 LANGUAGE numexpr cnumexpr
997 language = $2 | ($3 << SUBLANG_SHIFT);
1001 /* Menu resources. */
1004 id MENU suboptions BEG menuitems END
1006 define_menu ($1, &$3, $5);
1007 if (yychar != YYEMPTY)
1009 rcparse_discard_strings ();
1018 | menuitems menuitem
1026 for (pp = &$1->next; *pp != NULL; pp = &(*pp)->next)
1035 MENUITEM res_unicode_string cnumexpr menuitem_flags
1037 $$ = define_menuitem ($2, $3, $4, 0, 0, NULL);
1039 | MENUITEM SEPARATOR
1041 $$ = define_menuitem (NULL, 0, 0, 0, 0, NULL);
1043 | POPUP res_unicode_string menuitem_flags BEG menuitems END
1045 $$ = define_menuitem ($2, 0, $3, 0, 0, $5);
1054 | menuitem_flags ',' menuitem_flag
1058 | menuitem_flags menuitem_flag
1067 $$ = MENUITEM_CHECKED;
1071 $$ = MENUITEM_GRAYED;
1079 $$ = MENUITEM_INACTIVE;
1083 $$ = MENUITEM_MENUBARBREAK;
1087 $$ = MENUITEM_MENUBREAK;
1091 /* Menuex resources. */
1094 id MENUEX suboptions BEG menuexitems END
1096 define_menu ($1, &$3, $5);
1097 if (yychar != YYEMPTY)
1099 rcparse_discard_strings ();
1108 | menuexitems menuexitem
1116 for (pp = &$1->next; *pp != NULL; pp = &(*pp)->next)
1125 MENUITEM res_unicode_string
1127 $$ = define_menuitem ($2, 0, 0, 0, 0, NULL);
1129 | MENUITEM res_unicode_string cnumexpr
1131 $$ = define_menuitem ($2, $3, 0, 0, 0, NULL);
1133 | MENUITEM res_unicode_string cnumexpr cnumexpr optcnumexpr
1135 $$ = define_menuitem ($2, $3, $4, $5, 0, NULL);
1137 | MENUITEM SEPARATOR
1139 $$ = define_menuitem (NULL, 0, 0, 0, 0, NULL);
1141 | POPUP res_unicode_string BEG menuexitems END
1143 $$ = define_menuitem ($2, 0, 0, 0, 0, $4);
1145 | POPUP res_unicode_string cnumexpr BEG menuexitems END
1147 $$ = define_menuitem ($2, $3, 0, 0, 0, $5);
1149 | POPUP res_unicode_string cnumexpr cnumexpr BEG menuexitems END
1151 $$ = define_menuitem ($2, $3, $4, 0, 0, $6);
1153 | POPUP res_unicode_string cnumexpr cnumexpr cnumexpr optcnumexpr
1156 $$ = define_menuitem ($2, $3, $4, $5, $6, $8);
1160 /* Messagetable resources. */
1163 id MESSAGETABLE memflags_move file_name
1165 define_messagetable ($1, &$3, $4);
1166 if (yychar != YYEMPTY)
1168 rcparse_discard_strings ();
1172 /* We use a different lexing algorithm, because rcdata strings may
1173 contain embedded null bytes, and we need to know the length to use. */
1203 ri = define_rcdata_string ($1.s, $1.length);
1211 ri = define_rcdata_unistring ($1.s, $1.length);
1219 ri = define_rcdata_number ($1.val, $1.dword);
1223 | rcdata_data ',' sizedstring
1227 ri = define_rcdata_string ($3.s, $3.length);
1228 $$.first = $1.first;
1232 | rcdata_data ',' sizedunistring
1236 ri = define_rcdata_unistring ($3.s, $3.length);
1237 $$.first = $1.first;
1241 | rcdata_data ',' sizednumexpr
1245 ri = define_rcdata_number ($3.val, $3.dword);
1246 $$.first = $1.first;
1252 /* Stringtable resources. */
1255 STRINGTABLE suboptions BEG
1256 { sub_res_info = $2; }
1262 | string_data numexpr res_unicode_string
1264 define_stringtable (&sub_res_info, $2, $3);
1265 if (yychar != YYEMPTY)
1267 rcparse_discard_strings ();
1269 | string_data numexpr ',' res_unicode_string
1271 define_stringtable (&sub_res_info, $2, $4);
1272 if (yychar != YYEMPTY)
1274 rcparse_discard_strings ();
1291 $$.u.id = RT_RCDATA;
1296 $$.u.id = RT_MANIFEST;
1301 $$.u.id = RT_PLUGPLAY;
1311 $$.u.id = RT_DLGINCLUDE;
1316 $$.u.id = RT_DLGINIT;
1321 $$.u.id = RT_ANICURSOR;
1326 $$.u.id = RT_ANIICON;
1330 /* User defined resources. We accept general suboptions in the
1331 file_name case to keep the parser happy. */
1334 id rcdata_id suboptions BEG optrcdata_data END
1336 define_user_data ($1, $2, &$3, $5.first);
1337 if (yychar != YYEMPTY)
1339 rcparse_discard_strings ();
1341 | id rcdata_id suboptions file_name
1343 define_user_file ($1, $2, &$3, $4);
1344 if (yychar != YYEMPTY)
1346 rcparse_discard_strings ();
1351 id TOOLBAR suboptions numexpr cnumexpr BEG toolbar_data END
1353 define_toolbar ($1, &$3, $4, $5, $7);
1357 toolbar_data: /* empty */ { $$= NULL; }
1358 | toolbar_data BUTTON id
1360 rc_toolbar_item *c,*n;
1362 n= (rc_toolbar_item *)
1363 res_alloc (sizeof (rc_toolbar_item));
1365 while (c->next != NULL)
1377 | toolbar_data SEPARATOR
1379 rc_toolbar_item *c,*n;
1381 n= (rc_toolbar_item *)
1382 res_alloc (sizeof (rc_toolbar_item));
1384 while (c->next != NULL)
1399 /* Versioninfo resources. */
1402 id VERSIONINFO fixedverinfo BEG verblocks END
1404 define_versioninfo ($1, language, $3, $5);
1405 if (yychar != YYEMPTY)
1407 rcparse_discard_strings ();
1414 $$ = ((rc_fixed_versioninfo *)
1415 res_alloc (sizeof (rc_fixed_versioninfo)));
1416 memset ($$, 0, sizeof (rc_fixed_versioninfo));
1418 | fixedverinfo FILEVERSION numexpr cnumexpr cnumexpr cnumexpr
1420 $1->file_version_ms = ($3 << 16) | $4;
1421 $1->file_version_ls = ($5 << 16) | $6;
1424 | fixedverinfo PRODUCTVERSION numexpr cnumexpr cnumexpr cnumexpr
1426 $1->product_version_ms = ($3 << 16) | $4;
1427 $1->product_version_ls = ($5 << 16) | $6;
1430 | fixedverinfo FILEFLAGSMASK numexpr
1432 $1->file_flags_mask = $3;
1435 | fixedverinfo FILEFLAGS numexpr
1437 $1->file_flags = $3;
1440 | fixedverinfo FILEOS numexpr
1445 | fixedverinfo FILETYPE numexpr
1450 | fixedverinfo FILESUBTYPE numexpr
1452 $1->file_subtype = $3;
1457 /* To handle verblocks successfully, the lexer handles BLOCK
1458 specially. A BLOCK "StringFileInfo" is returned as
1459 BLOCKSTRINGFILEINFO. A BLOCK "VarFileInfo" is returned as
1460 BLOCKVARFILEINFO. A BLOCK with some other string returns BLOCK
1461 with the string as the value. */
1468 | verblocks BLOCKSTRINGFILEINFO BEG BLOCK BEG vervals END END
1470 $$ = append_ver_stringfileinfo ($1, $4, $6);
1472 | verblocks BLOCKVARFILEINFO BEG VALUE res_unicode_string vertrans END
1474 $$ = append_ver_varfileinfo ($1, $5, $6);
1483 | vervals VALUE res_unicode_string ',' res_unicode_string
1485 $$ = append_verval ($1, $3, $5);
1494 | vertrans cnumexpr cnumexpr
1496 $$ = append_vertrans ($1, $2, $3);
1500 /* A resource ID. */
1511 res_unistring_to_id (&$$, $1);
1515 /* A resource reference. */
1525 unicode_from_ascii ((rc_uint_type *) NULL, &h, $1);
1539 res_unistring_to_id (&$$, $1);
1543 res_unistring_to_id (&$$, $1);
1547 /* Generic suboptions. These may appear before the BEGIN in any
1548 multiline statement. */
1553 memset (&$$, 0, sizeof (rc_res_res_info));
1554 $$.language = language;
1555 /* FIXME: Is this the right default? */
1556 $$.memflags = MEMFLAG_MOVEABLE | MEMFLAG_PURE | MEMFLAG_DISCARDABLE;
1558 | suboptions memflag
1561 $$.memflags |= $2.on;
1562 $$.memflags &=~ $2.off;
1564 | suboptions CHARACTERISTICS numexpr
1567 $$.characteristics = $3;
1569 | suboptions LANGUAGE numexpr cnumexpr
1572 $$.language = $3 | ($4 << SUBLANG_SHIFT);
1574 | suboptions VERSIONK numexpr
1581 /* Memory flags which default to MOVEABLE and DISCARDABLE. */
1583 memflags_move_discard:
1586 memset (&$$, 0, sizeof (rc_res_res_info));
1587 $$.language = language;
1588 $$.memflags = MEMFLAG_MOVEABLE | MEMFLAG_DISCARDABLE;
1590 | memflags_move_discard memflag
1593 $$.memflags |= $2.on;
1594 $$.memflags &=~ $2.off;
1598 /* Memory flags which default to MOVEABLE. */
1603 memset (&$$, 0, sizeof (rc_res_res_info));
1604 $$.language = language;
1605 $$.memflags = MEMFLAG_MOVEABLE | MEMFLAG_PURE | MEMFLAG_DISCARDABLE;
1607 | memflags_move memflag
1610 $$.memflags |= $2.on;
1611 $$.memflags &=~ $2.off;
1615 /* Memory flags. This returns a struct with two integers, because we
1616 sometimes want to set bits and we sometimes want to clear them. */
1621 $$.on = MEMFLAG_MOVEABLE;
1627 $$.off = MEMFLAG_MOVEABLE;
1631 $$.on = MEMFLAG_PURE;
1637 $$.off = MEMFLAG_PURE;
1641 $$.on = MEMFLAG_PRELOAD;
1647 $$.off = MEMFLAG_PRELOAD;
1651 $$.on = MEMFLAG_DISCARDABLE;
1672 $$ = unichar_dup ($1);
1677 unicode_from_ascii ((rc_uint_type *) NULL, &h, $1);
1687 | sizedstring SIZEDSTRING
1689 rc_uint_type l = $1.length + $2.length;
1690 char *h = (char *) res_alloc (l);
1691 memcpy (h, $1.s, $1.length);
1692 memcpy (h + $1.length, $2.s, $2.length);
1703 | sizedunistring SIZEDUNISTRING
1705 rc_uint_type l = $1.length + $2.length;
1706 unichar *h = (unichar *) res_alloc (l * sizeof (unichar));
1707 memcpy (h, $1.s, $1.length * sizeof (unichar));
1708 memcpy (h + $1.length, $2.s, $2.length * sizeof (unichar));
1714 /* A style expression. This changes the static variable STYLE. We do
1715 it this way because rc appears to permit a style to be set to
1717 WS_GROUP | NOT WS_TABSTOP
1718 to mean that a default of WS_TABSTOP should be removed. Anything
1719 which wants to accept a style must first set STYLE to the default
1720 value. The styleexpr nonterminal will change STYLE as specified by
1721 the user. Note that we do not accept arbitrary expressions here,
1722 just numbers separated by '|'. */
1733 | styleexpr '|' parennumber
1737 | styleexpr '|' NOT parennumber
1754 /* An optional expression with a leading comma. */
1767 /* An expression with a leading comma. */
1776 /* A possibly negated numeric expression. */
1785 /* A possibly negated expression with a size. */
1792 | '(' sizednumexpr ')'
1796 | '~' sizednumexpr %prec '~'
1799 $$.dword = $2.dword;
1801 | '-' sizednumexpr %prec NEG
1804 $$.dword = $2.dword;
1806 | sizednumexpr '*' sizednumexpr
1808 $$.val = $1.val * $3.val;
1809 $$.dword = $1.dword || $3.dword;
1811 | sizednumexpr '/' sizednumexpr
1813 $$.val = $1.val / $3.val;
1814 $$.dword = $1.dword || $3.dword;
1816 | sizednumexpr '%' sizednumexpr
1818 $$.val = $1.val % $3.val;
1819 $$.dword = $1.dword || $3.dword;
1821 | sizednumexpr '+' sizednumexpr
1823 $$.val = $1.val + $3.val;
1824 $$.dword = $1.dword || $3.dword;
1826 | sizednumexpr '-' sizednumexpr
1828 $$.val = $1.val - $3.val;
1829 $$.dword = $1.dword || $3.dword;
1831 | sizednumexpr '&' sizednumexpr
1833 $$.val = $1.val & $3.val;
1834 $$.dword = $1.dword || $3.dword;
1836 | sizednumexpr '^' sizednumexpr
1838 $$.val = $1.val ^ $3.val;
1839 $$.dword = $1.dword || $3.dword;
1841 | sizednumexpr '|' sizednumexpr
1843 $$.val = $1.val | $3.val;
1844 $$.dword = $1.dword || $3.dword;
1848 /* An expression with a leading comma which does not use unary
1858 /* An expression which does not use unary negation. */
1867 /* An expression which does not use unary negation. We separate unary
1868 negation to avoid parsing conflicts when two numeric expressions
1869 appear consecutively. */
1876 | '(' sizednumexpr ')'
1880 | '~' sizednumexpr %prec '~'
1883 $$.dword = $2.dword;
1885 | sizedposnumexpr '*' sizednumexpr
1887 $$.val = $1.val * $3.val;
1888 $$.dword = $1.dword || $3.dword;
1890 | sizedposnumexpr '/' sizednumexpr
1892 $$.val = $1.val / $3.val;
1893 $$.dword = $1.dword || $3.dword;
1895 | sizedposnumexpr '%' sizednumexpr
1897 $$.val = $1.val % $3.val;
1898 $$.dword = $1.dword || $3.dword;
1900 | sizedposnumexpr '+' sizednumexpr
1902 $$.val = $1.val + $3.val;
1903 $$.dword = $1.dword || $3.dword;
1905 | sizedposnumexpr '-' sizednumexpr
1907 $$.val = $1.val - $3.val;
1908 $$.dword = $1.dword || $3.dword;
1910 | sizedposnumexpr '&' sizednumexpr
1912 $$.val = $1.val & $3.val;
1913 $$.dword = $1.dword || $3.dword;
1915 | sizedposnumexpr '^' sizednumexpr
1917 $$.val = $1.val ^ $3.val;
1918 $$.dword = $1.dword || $3.dword;
1920 | sizedposnumexpr '|' sizednumexpr
1922 $$.val = $1.val | $3.val;
1923 $$.dword = $1.dword || $3.dword;
1929 /* Set the language from the command line. */
1932 rcparse_set_language (int lang)