OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-old/] [binutils-2.18.50/] [binutils/] [rcparse.y] - Diff between revs 156 and 816

Go to most recent revision | Only display areas with differences | Details | Blame | View Log

Rev 156 Rev 816
%{ /* rcparse.y -- parser for Windows rc files
%{ /* rcparse.y -- parser for Windows rc files
   Copyright 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2005, 2007
   Copyright 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2005, 2007
   Free Software Foundation, Inc.
   Free Software Foundation, Inc.
   Written by Ian Lance Taylor, Cygnus Support.
   Written by Ian Lance Taylor, Cygnus Support.
   Extended by Kai Tietz, Onevision.
   Extended by Kai Tietz, Onevision.
   This file is part of GNU Binutils.
   This file is part of GNU Binutils.
   This program is free software; you can redistribute it and/or modify
   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 3 of the License, or
   the Free Software Foundation; either version 3 of the License, or
   (at your option) any later version.
   (at your option) any later version.
   This program is distributed in the hope that it will be useful,
   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.
   GNU General Public License for more details.
   You should have received a copy of the GNU General Public License
   You should have received a copy of the GNU General Public License
   along with this program; if not, write to the Free Software
   along with this program; if not, write to the Free Software
   Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA
   Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA
   02110-1301, USA.  */
   02110-1301, USA.  */
/* This is a parser for Windows rc files.  It is based on the parser
/* This is a parser for Windows rc files.  It is based on the parser
   by Gunther Ebert .  */
   by Gunther Ebert .  */
#include "sysdep.h"
#include "sysdep.h"
#include "bfd.h"
#include "bfd.h"
#include "bucomm.h"
#include "bucomm.h"
#include "libiberty.h"
#include "libiberty.h"
#include "windres.h"
#include "windres.h"
#include "safe-ctype.h"
#include "safe-ctype.h"
/* The current language.  */
/* The current language.  */
static unsigned short language;
static unsigned short language;
/* The resource information during a sub statement.  */
/* The resource information during a sub statement.  */
static rc_res_res_info sub_res_info;
static rc_res_res_info sub_res_info;
/* Dialog information.  This is built by the nonterminals styles and
/* Dialog information.  This is built by the nonterminals styles and
   controls.  */
   controls.  */
static rc_dialog dialog;
static rc_dialog dialog;
/* This is used when building a style.  It is modified by the
/* This is used when building a style.  It is modified by the
   nonterminal styleexpr.  */
   nonterminal styleexpr.  */
static unsigned long style;
static unsigned long style;
/* These are used when building a control.  They are set before using
/* These are used when building a control.  They are set before using
   control_params.  */
   control_params.  */
static rc_uint_type base_style;
static rc_uint_type base_style;
static rc_uint_type default_style;
static rc_uint_type default_style;
static rc_res_id class;
static rc_res_id class;
static rc_res_id res_text_field;
static rc_res_id res_text_field;
static unichar null_unichar;
static unichar null_unichar;
/* This is used for COMBOBOX, LISTBOX and EDITTEXT which
/* This is used for COMBOBOX, LISTBOX and EDITTEXT which
   do not allow resource 'text' field in control definition. */
   do not allow resource 'text' field in control definition. */
static const rc_res_id res_null_text = { 1, {{0, &null_unichar}}};
static const rc_res_id res_null_text = { 1, {{0, &null_unichar}}};
%}
%}
%union
%union
{
{
  rc_accelerator acc;
  rc_accelerator acc;
  rc_accelerator *pacc;
  rc_accelerator *pacc;
  rc_dialog_control *dialog_control;
  rc_dialog_control *dialog_control;
  rc_menuitem *menuitem;
  rc_menuitem *menuitem;
  struct
  struct
  {
  {
    rc_rcdata_item *first;
    rc_rcdata_item *first;
    rc_rcdata_item *last;
    rc_rcdata_item *last;
  } rcdata;
  } rcdata;
  rc_rcdata_item *rcdata_item;
  rc_rcdata_item *rcdata_item;
  rc_fixed_versioninfo *fixver;
  rc_fixed_versioninfo *fixver;
  rc_ver_info *verinfo;
  rc_ver_info *verinfo;
  rc_ver_stringinfo *verstring;
  rc_ver_stringinfo *verstring;
  rc_ver_varinfo *vervar;
  rc_ver_varinfo *vervar;
  rc_toolbar_item *toobar_item;
  rc_toolbar_item *toobar_item;
  rc_res_id id;
  rc_res_id id;
  rc_res_res_info res_info;
  rc_res_res_info res_info;
  struct
  struct
  {
  {
    rc_uint_type on;
    rc_uint_type on;
    rc_uint_type off;
    rc_uint_type off;
  } memflags;
  } memflags;
  struct
  struct
  {
  {
    rc_uint_type val;
    rc_uint_type val;
    /* Nonzero if this number was explicitly specified as long.  */
    /* Nonzero if this number was explicitly specified as long.  */
    int dword;
    int dword;
  } i;
  } i;
  rc_uint_type il;
  rc_uint_type il;
  rc_uint_type is;
  rc_uint_type is;
  const char *s;
  const char *s;
  struct
  struct
  {
  {
    rc_uint_type length;
    rc_uint_type length;
    const char *s;
    const char *s;
  } ss;
  } ss;
  unichar *uni;
  unichar *uni;
  struct
  struct
  {
  {
    rc_uint_type length;
    rc_uint_type length;
    const unichar *s;
    const unichar *s;
  } suni;
  } suni;
};
};
%token BEG END
%token BEG END
%token ACCELERATORS VIRTKEY ASCII NOINVERT SHIFT CONTROL ALT
%token ACCELERATORS VIRTKEY ASCII NOINVERT SHIFT CONTROL ALT
%token BITMAP
%token BITMAP
%token CURSOR
%token CURSOR
%token DIALOG DIALOGEX EXSTYLE CAPTION CLASS STYLE
%token DIALOG DIALOGEX EXSTYLE CAPTION CLASS STYLE
%token AUTO3STATE AUTOCHECKBOX AUTORADIOBUTTON CHECKBOX COMBOBOX CTEXT
%token AUTO3STATE AUTOCHECKBOX AUTORADIOBUTTON CHECKBOX COMBOBOX CTEXT
%token DEFPUSHBUTTON EDITTEXT GROUPBOX LISTBOX LTEXT PUSHBOX PUSHBUTTON
%token DEFPUSHBUTTON EDITTEXT GROUPBOX LISTBOX LTEXT PUSHBOX PUSHBUTTON
%token RADIOBUTTON RTEXT SCROLLBAR STATE3 USERBUTTON
%token RADIOBUTTON RTEXT SCROLLBAR STATE3 USERBUTTON
%token BEDIT HEDIT IEDIT
%token BEDIT HEDIT IEDIT
%token FONT
%token FONT
%token ICON
%token ICON
%token ANICURSOR ANIICON DLGINCLUDE DLGINIT FONTDIR HTML MANIFEST PLUGPLAY VXD TOOLBAR BUTTON
%token ANICURSOR ANIICON DLGINCLUDE DLGINIT FONTDIR HTML MANIFEST PLUGPLAY VXD TOOLBAR BUTTON
%token LANGUAGE CHARACTERISTICS VERSIONK
%token LANGUAGE CHARACTERISTICS VERSIONK
%token MENU MENUEX MENUITEM SEPARATOR POPUP CHECKED GRAYED HELP INACTIVE
%token MENU MENUEX MENUITEM SEPARATOR POPUP CHECKED GRAYED HELP INACTIVE
%token MENUBARBREAK MENUBREAK
%token MENUBARBREAK MENUBREAK
%token MESSAGETABLE
%token MESSAGETABLE
%token RCDATA
%token RCDATA
%token STRINGTABLE
%token STRINGTABLE
%token VERSIONINFO FILEVERSION PRODUCTVERSION FILEFLAGSMASK FILEFLAGS
%token VERSIONINFO FILEVERSION PRODUCTVERSION FILEFLAGSMASK FILEFLAGS
%token FILEOS FILETYPE FILESUBTYPE BLOCKSTRINGFILEINFO BLOCKVARFILEINFO
%token FILEOS FILETYPE FILESUBTYPE BLOCKSTRINGFILEINFO BLOCKVARFILEINFO
%token VALUE
%token VALUE
%token  BLOCK
%token  BLOCK
%token MOVEABLE FIXED PURE IMPURE PRELOAD LOADONCALL DISCARDABLE
%token MOVEABLE FIXED PURE IMPURE PRELOAD LOADONCALL DISCARDABLE
%token NOT
%token NOT
%token  QUOTEDUNISTRING
%token  QUOTEDUNISTRING
%token  QUOTEDSTRING STRING
%token  QUOTEDSTRING STRING
%token  NUMBER
%token  NUMBER
%token  SIZEDUNISTRING
%token  SIZEDUNISTRING
%token  SIZEDSTRING
%token  SIZEDSTRING
%token IGNORED_TOKEN
%token IGNORED_TOKEN
%type  acc_entries
%type  acc_entries
%type  acc_entry acc_event
%type  acc_entry acc_event
%type  control control_params
%type  control control_params
%type  menuitems menuitem menuexitems menuexitem
%type  menuitems menuitem menuexitems menuexitem
%type  optrcdata_data optrcdata_data_int rcdata_data
%type  optrcdata_data optrcdata_data_int rcdata_data
%type  opt_control_data
%type  opt_control_data
%type  fixedverinfo
%type  fixedverinfo
%type  verblocks
%type  verblocks
%type  vervals
%type  vervals
%type  vertrans
%type  vertrans
%type  toolbar_data
%type  toolbar_data
%type  suboptions memflags_move_discard memflags_move
%type  suboptions memflags_move_discard memflags_move
%type  memflag
%type  memflag
%type  id rcdata_id optresidc resref resid cresid
%type  id rcdata_id optresidc resref resid cresid
%type  exstyle parennumber
%type  exstyle parennumber
%type  numexpr posnumexpr cnumexpr optcnumexpr cposnumexpr
%type  numexpr posnumexpr cnumexpr optcnumexpr cposnumexpr
%type  acc_options acc_option menuitem_flags menuitem_flag
%type  acc_options acc_option menuitem_flags menuitem_flag
%type  file_name
%type  file_name
%type  res_unicode_string resname res_unicode_string_concat
%type  res_unicode_string resname res_unicode_string_concat
%type  sizedstring
%type  sizedstring
%type  sizedunistring
%type  sizedunistring
%type  sizednumexpr sizedposnumexpr
%type  sizednumexpr sizedposnumexpr
%left '|'
%left '|'
%left '^'
%left '^'
%left '&'
%left '&'
%left '+' '-'
%left '+' '-'
%left '*' '/' '%'
%left '*' '/' '%'
%right '~' NEG
%right '~' NEG
%%
%%
input:
input:
          /* empty */
          /* empty */
        | input accelerator
        | input accelerator
        | input bitmap
        | input bitmap
        | input cursor
        | input cursor
        | input dialog
        | input dialog
        | input font
        | input font
        | input icon
        | input icon
        | input language
        | input language
        | input menu
        | input menu
        | input menuex
        | input menuex
        | input messagetable
        | input messagetable
        | input stringtable
        | input stringtable
        | input toolbar
        | input toolbar
        | input user
        | input user
        | input versioninfo
        | input versioninfo
        | input IGNORED_TOKEN
        | input IGNORED_TOKEN
        ;
        ;
/* Accelerator resources.  */
/* Accelerator resources.  */
accelerator:
accelerator:
          id ACCELERATORS suboptions BEG acc_entries END
          id ACCELERATORS suboptions BEG acc_entries END
          {
          {
            define_accelerator ($1, &$3, $5);
            define_accelerator ($1, &$3, $5);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        ;
        ;
acc_entries:
acc_entries:
          /* empty */
          /* empty */
          {
          {
            $$ = NULL;
            $$ = NULL;
          }
          }
        | acc_entries acc_entry
        | acc_entries acc_entry
          {
          {
            rc_accelerator *a;
            rc_accelerator *a;
            a = (rc_accelerator *) res_alloc (sizeof *a);
            a = (rc_accelerator *) res_alloc (sizeof *a);
            *a = $2;
            *a = $2;
            if ($1 == NULL)
            if ($1 == NULL)
              $$ = a;
              $$ = a;
            else
            else
              {
              {
                rc_accelerator **pp;
                rc_accelerator **pp;
                for (pp = &$1->next; *pp != NULL; pp = &(*pp)->next)
                for (pp = &$1->next; *pp != NULL; pp = &(*pp)->next)
                  ;
                  ;
                *pp = a;
                *pp = a;
                $$ = $1;
                $$ = $1;
              }
              }
          }
          }
        ;
        ;
acc_entry:
acc_entry:
          acc_event cposnumexpr
          acc_event cposnumexpr
          {
          {
            $$ = $1;
            $$ = $1;
            $$.id = $2;
            $$.id = $2;
          }
          }
        | acc_event cposnumexpr ',' acc_options
        | acc_event cposnumexpr ',' acc_options
          {
          {
            $$ = $1;
            $$ = $1;
            $$.id = $2;
            $$.id = $2;
            $$.flags |= $4;
            $$.flags |= $4;
            if (($$.flags & ACC_VIRTKEY) == 0
            if (($$.flags & ACC_VIRTKEY) == 0
                && ($$.flags & (ACC_SHIFT | ACC_CONTROL)) != 0)
                && ($$.flags & (ACC_SHIFT | ACC_CONTROL)) != 0)
              rcparse_warning (_("inappropriate modifiers for non-VIRTKEY"));
              rcparse_warning (_("inappropriate modifiers for non-VIRTKEY"));
          }
          }
        ;
        ;
acc_event:
acc_event:
          QUOTEDSTRING
          QUOTEDSTRING
          {
          {
            const char *s = $1;
            const char *s = $1;
            char ch;
            char ch;
            $$.next = NULL;
            $$.next = NULL;
            $$.id = 0;
            $$.id = 0;
            ch = *s;
            ch = *s;
            if (ch != '^')
            if (ch != '^')
              $$.flags = 0;
              $$.flags = 0;
            else
            else
              {
              {
                $$.flags = ACC_CONTROL | ACC_VIRTKEY;
                $$.flags = ACC_CONTROL | ACC_VIRTKEY;
                ++s;
                ++s;
                ch = TOUPPER (s[0]);
                ch = TOUPPER (s[0]);
              }
              }
            $$.key = ch;
            $$.key = ch;
            if (s[1] != '\0')
            if (s[1] != '\0')
              rcparse_warning (_("accelerator should only be one character"));
              rcparse_warning (_("accelerator should only be one character"));
          }
          }
        | posnumexpr
        | posnumexpr
          {
          {
            $$.next = NULL;
            $$.next = NULL;
            $$.flags = 0;
            $$.flags = 0;
            $$.id = 0;
            $$.id = 0;
            $$.key = $1;
            $$.key = $1;
          }
          }
        ;
        ;
acc_options:
acc_options:
          acc_option
          acc_option
          {
          {
            $$ = $1;
            $$ = $1;
          }
          }
        | acc_options ',' acc_option
        | acc_options ',' acc_option
          {
          {
            $$ = $1 | $3;
            $$ = $1 | $3;
          }
          }
        /* I've had one report that the comma is optional.  */
        /* I've had one report that the comma is optional.  */
        | acc_options acc_option
        | acc_options acc_option
          {
          {
            $$ = $1 | $2;
            $$ = $1 | $2;
          }
          }
        ;
        ;
acc_option:
acc_option:
          VIRTKEY
          VIRTKEY
          {
          {
            $$ = ACC_VIRTKEY;
            $$ = ACC_VIRTKEY;
          }
          }
        | ASCII
        | ASCII
          {
          {
            /* This is just the absence of VIRTKEY.  */
            /* This is just the absence of VIRTKEY.  */
            $$ = 0;
            $$ = 0;
          }
          }
        | NOINVERT
        | NOINVERT
          {
          {
            $$ = ACC_NOINVERT;
            $$ = ACC_NOINVERT;
          }
          }
        | SHIFT
        | SHIFT
          {
          {
            $$ = ACC_SHIFT;
            $$ = ACC_SHIFT;
          }
          }
        | CONTROL
        | CONTROL
          {
          {
            $$ = ACC_CONTROL;
            $$ = ACC_CONTROL;
          }
          }
        | ALT
        | ALT
          {
          {
            $$ = ACC_ALT;
            $$ = ACC_ALT;
          }
          }
        ;
        ;
/* Bitmap resources.  */
/* Bitmap resources.  */
bitmap:
bitmap:
          id BITMAP memflags_move file_name
          id BITMAP memflags_move file_name
          {
          {
            define_bitmap ($1, &$3, $4);
            define_bitmap ($1, &$3, $4);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        ;
        ;
/* Cursor resources.  */
/* Cursor resources.  */
cursor:
cursor:
          id CURSOR memflags_move_discard file_name
          id CURSOR memflags_move_discard file_name
          {
          {
            define_cursor ($1, &$3, $4);
            define_cursor ($1, &$3, $4);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        ;
        ;
/* Dialog resources.  */
/* Dialog resources.  */
dialog:
dialog:
          id DIALOG memflags_move exstyle posnumexpr cnumexpr cnumexpr
          id DIALOG memflags_move exstyle posnumexpr cnumexpr cnumexpr
            cnumexpr
            cnumexpr
            {
            {
              memset (&dialog, 0, sizeof dialog);
              memset (&dialog, 0, sizeof dialog);
              dialog.x = $5;
              dialog.x = $5;
              dialog.y = $6;
              dialog.y = $6;
              dialog.width = $7;
              dialog.width = $7;
              dialog.height = $8;
              dialog.height = $8;
              dialog.style = WS_POPUP | WS_BORDER | WS_SYSMENU;
              dialog.style = WS_POPUP | WS_BORDER | WS_SYSMENU;
              dialog.exstyle = $4;
              dialog.exstyle = $4;
              dialog.menu.named = 1;
              dialog.menu.named = 1;
              dialog.class.named = 1;
              dialog.class.named = 1;
              dialog.font = NULL;
              dialog.font = NULL;
              dialog.ex = NULL;
              dialog.ex = NULL;
              dialog.controls = NULL;
              dialog.controls = NULL;
              sub_res_info = $3;
              sub_res_info = $3;
              style = 0;
              style = 0;
            }
            }
            styles BEG controls END
            styles BEG controls END
          {
          {
            define_dialog ($1, &sub_res_info, &dialog);
            define_dialog ($1, &sub_res_info, &dialog);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        | id DIALOGEX memflags_move exstyle posnumexpr cnumexpr cnumexpr
        | id DIALOGEX memflags_move exstyle posnumexpr cnumexpr cnumexpr
            cnumexpr
            cnumexpr
            {
            {
              memset (&dialog, 0, sizeof dialog);
              memset (&dialog, 0, sizeof dialog);
              dialog.x = $5;
              dialog.x = $5;
              dialog.y = $6;
              dialog.y = $6;
              dialog.width = $7;
              dialog.width = $7;
              dialog.height = $8;
              dialog.height = $8;
              dialog.style = WS_POPUP | WS_BORDER | WS_SYSMENU;
              dialog.style = WS_POPUP | WS_BORDER | WS_SYSMENU;
              dialog.exstyle = $4;
              dialog.exstyle = $4;
              dialog.menu.named = 1;
              dialog.menu.named = 1;
              dialog.class.named = 1;
              dialog.class.named = 1;
              dialog.font = NULL;
              dialog.font = NULL;
              dialog.ex = ((rc_dialog_ex *)
              dialog.ex = ((rc_dialog_ex *)
                           res_alloc (sizeof (rc_dialog_ex)));
                           res_alloc (sizeof (rc_dialog_ex)));
              memset (dialog.ex, 0, sizeof (rc_dialog_ex));
              memset (dialog.ex, 0, sizeof (rc_dialog_ex));
              dialog.controls = NULL;
              dialog.controls = NULL;
              sub_res_info = $3;
              sub_res_info = $3;
              style = 0;
              style = 0;
            }
            }
            styles BEG controls END
            styles BEG controls END
          {
          {
            define_dialog ($1, &sub_res_info, &dialog);
            define_dialog ($1, &sub_res_info, &dialog);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        | id DIALOGEX memflags_move exstyle posnumexpr cnumexpr cnumexpr
        | id DIALOGEX memflags_move exstyle posnumexpr cnumexpr cnumexpr
            cnumexpr cnumexpr
            cnumexpr cnumexpr
            {
            {
              memset (&dialog, 0, sizeof dialog);
              memset (&dialog, 0, sizeof dialog);
              dialog.x = $5;
              dialog.x = $5;
              dialog.y = $6;
              dialog.y = $6;
              dialog.width = $7;
              dialog.width = $7;
              dialog.height = $8;
              dialog.height = $8;
              dialog.style = WS_POPUP | WS_BORDER | WS_SYSMENU;
              dialog.style = WS_POPUP | WS_BORDER | WS_SYSMENU;
              dialog.exstyle = $4;
              dialog.exstyle = $4;
              dialog.menu.named = 1;
              dialog.menu.named = 1;
              dialog.class.named = 1;
              dialog.class.named = 1;
              dialog.font = NULL;
              dialog.font = NULL;
              dialog.ex = ((rc_dialog_ex *)
              dialog.ex = ((rc_dialog_ex *)
                           res_alloc (sizeof (rc_dialog_ex)));
                           res_alloc (sizeof (rc_dialog_ex)));
              memset (dialog.ex, 0, sizeof (rc_dialog_ex));
              memset (dialog.ex, 0, sizeof (rc_dialog_ex));
              dialog.ex->help = $9;
              dialog.ex->help = $9;
              dialog.controls = NULL;
              dialog.controls = NULL;
              sub_res_info = $3;
              sub_res_info = $3;
              style = 0;
              style = 0;
            }
            }
            styles BEG controls END
            styles BEG controls END
          {
          {
            define_dialog ($1, &sub_res_info, &dialog);
            define_dialog ($1, &sub_res_info, &dialog);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        ;
        ;
exstyle:
exstyle:
          /* empty */
          /* empty */
          {
          {
            $$ = 0;
            $$ = 0;
          }
          }
        | EXSTYLE '=' numexpr
        | EXSTYLE '=' numexpr
          {
          {
            $$ = $3;
            $$ = $3;
          }
          }
        ;
        ;
styles:
styles:
          /* empty */
          /* empty */
        | styles CAPTION res_unicode_string_concat
        | styles CAPTION res_unicode_string_concat
          {
          {
            dialog.style |= WS_CAPTION;
            dialog.style |= WS_CAPTION;
            style |= WS_CAPTION;
            style |= WS_CAPTION;
            dialog.caption = $3;
            dialog.caption = $3;
          }
          }
        | styles CLASS id
        | styles CLASS id
          {
          {
            dialog.class = $3;
            dialog.class = $3;
          }
          }
        | styles STYLE
        | styles STYLE
            styleexpr
            styleexpr
          {
          {
            dialog.style = style;
            dialog.style = style;
          }
          }
        | styles EXSTYLE numexpr
        | styles EXSTYLE numexpr
          {
          {
            dialog.exstyle = $3;
            dialog.exstyle = $3;
          }
          }
        | styles CLASS res_unicode_string_concat
        | styles CLASS res_unicode_string_concat
          {
          {
            res_unistring_to_id (& dialog.class, $3);
            res_unistring_to_id (& dialog.class, $3);
          }
          }
        | styles FONT numexpr ',' res_unicode_string_concat
        | styles FONT numexpr ',' res_unicode_string_concat
          {
          {
            dialog.style |= DS_SETFONT;
            dialog.style |= DS_SETFONT;
            style |= DS_SETFONT;
            style |= DS_SETFONT;
            dialog.pointsize = $3;
            dialog.pointsize = $3;
            dialog.font = $5;
            dialog.font = $5;
            if (dialog.ex != NULL)
            if (dialog.ex != NULL)
              {
              {
                dialog.ex->weight = 0;
                dialog.ex->weight = 0;
                dialog.ex->italic = 0;
                dialog.ex->italic = 0;
                dialog.ex->charset = 1;
                dialog.ex->charset = 1;
              }
              }
          }
          }
        | styles FONT numexpr ',' res_unicode_string_concat cnumexpr
        | styles FONT numexpr ',' res_unicode_string_concat cnumexpr
          {
          {
            dialog.style |= DS_SETFONT;
            dialog.style |= DS_SETFONT;
            style |= DS_SETFONT;
            style |= DS_SETFONT;
            dialog.pointsize = $3;
            dialog.pointsize = $3;
            dialog.font = $5;
            dialog.font = $5;
            if (dialog.ex == NULL)
            if (dialog.ex == NULL)
              rcparse_warning (_("extended FONT requires DIALOGEX"));
              rcparse_warning (_("extended FONT requires DIALOGEX"));
            else
            else
              {
              {
                dialog.ex->weight = $6;
                dialog.ex->weight = $6;
                dialog.ex->italic = 0;
                dialog.ex->italic = 0;
                dialog.ex->charset = 1;
                dialog.ex->charset = 1;
              }
              }
          }
          }
        | styles FONT numexpr ',' res_unicode_string_concat cnumexpr cnumexpr
        | styles FONT numexpr ',' res_unicode_string_concat cnumexpr cnumexpr
          {
          {
            dialog.style |= DS_SETFONT;
            dialog.style |= DS_SETFONT;
            style |= DS_SETFONT;
            style |= DS_SETFONT;
            dialog.pointsize = $3;
            dialog.pointsize = $3;
            dialog.font = $5;
            dialog.font = $5;
            if (dialog.ex == NULL)
            if (dialog.ex == NULL)
              rcparse_warning (_("extended FONT requires DIALOGEX"));
              rcparse_warning (_("extended FONT requires DIALOGEX"));
            else
            else
              {
              {
                dialog.ex->weight = $6;
                dialog.ex->weight = $6;
                dialog.ex->italic = $7;
                dialog.ex->italic = $7;
                dialog.ex->charset = 1;
                dialog.ex->charset = 1;
              }
              }
          }
          }
        | styles FONT numexpr ',' res_unicode_string_concat cnumexpr cnumexpr cnumexpr
        | styles FONT numexpr ',' res_unicode_string_concat cnumexpr cnumexpr cnumexpr
          {
          {
            dialog.style |= DS_SETFONT;
            dialog.style |= DS_SETFONT;
            style |= DS_SETFONT;
            style |= DS_SETFONT;
            dialog.pointsize = $3;
            dialog.pointsize = $3;
            dialog.font = $5;
            dialog.font = $5;
            if (dialog.ex == NULL)
            if (dialog.ex == NULL)
              rcparse_warning (_("extended FONT requires DIALOGEX"));
              rcparse_warning (_("extended FONT requires DIALOGEX"));
            else
            else
              {
              {
                dialog.ex->weight = $6;
                dialog.ex->weight = $6;
                dialog.ex->italic = $7;
                dialog.ex->italic = $7;
                dialog.ex->charset = $8;
                dialog.ex->charset = $8;
              }
              }
          }
          }
        | styles MENU id
        | styles MENU id
          {
          {
            dialog.menu = $3;
            dialog.menu = $3;
          }
          }
        | styles CHARACTERISTICS numexpr
        | styles CHARACTERISTICS numexpr
          {
          {
            sub_res_info.characteristics = $3;
            sub_res_info.characteristics = $3;
          }
          }
        | styles LANGUAGE numexpr cnumexpr
        | styles LANGUAGE numexpr cnumexpr
          {
          {
            sub_res_info.language = $3 | ($4 << SUBLANG_SHIFT);
            sub_res_info.language = $3 | ($4 << SUBLANG_SHIFT);
          }
          }
        | styles VERSIONK numexpr
        | styles VERSIONK numexpr
          {
          {
            sub_res_info.version = $3;
            sub_res_info.version = $3;
          }
          }
        ;
        ;
controls:
controls:
          /* empty */
          /* empty */
        | controls control
        | controls control
          {
          {
            rc_dialog_control **pp;
            rc_dialog_control **pp;
            for (pp = &dialog.controls; *pp != NULL; pp = &(*pp)->next)
            for (pp = &dialog.controls; *pp != NULL; pp = &(*pp)->next)
              ;
              ;
            *pp = $2;
            *pp = $2;
          }
          }
        ;
        ;
control:
control:
          AUTO3STATE optresidc
          AUTO3STATE optresidc
            {
            {
              default_style = BS_AUTO3STATE | WS_TABSTOP;
              default_style = BS_AUTO3STATE | WS_TABSTOP;
              base_style = BS_AUTO3STATE;
              base_style = BS_AUTO3STATE;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_BUTTON;
              class.u.id = CTL_BUTTON;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | AUTOCHECKBOX optresidc
        | AUTOCHECKBOX optresidc
            {
            {
              default_style = BS_AUTOCHECKBOX | WS_TABSTOP;
              default_style = BS_AUTOCHECKBOX | WS_TABSTOP;
              base_style = BS_AUTOCHECKBOX;
              base_style = BS_AUTOCHECKBOX;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_BUTTON;
              class.u.id = CTL_BUTTON;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | AUTORADIOBUTTON optresidc
        | AUTORADIOBUTTON optresidc
            {
            {
              default_style = BS_AUTORADIOBUTTON | WS_TABSTOP;
              default_style = BS_AUTORADIOBUTTON | WS_TABSTOP;
              base_style = BS_AUTORADIOBUTTON;
              base_style = BS_AUTORADIOBUTTON;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_BUTTON;
              class.u.id = CTL_BUTTON;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | BEDIT optresidc
        | BEDIT optresidc
            {
            {
              default_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              default_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              base_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              base_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_EDIT;
              class.u.id = CTL_EDIT;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
            if (dialog.ex == NULL)
            if (dialog.ex == NULL)
              rcparse_warning (_("BEDIT requires DIALOGEX"));
              rcparse_warning (_("BEDIT requires DIALOGEX"));
            res_string_to_id (&$$->class, "BEDIT");
            res_string_to_id (&$$->class, "BEDIT");
          }
          }
        | CHECKBOX optresidc
        | CHECKBOX optresidc
            {
            {
              default_style = BS_CHECKBOX | WS_TABSTOP;
              default_style = BS_CHECKBOX | WS_TABSTOP;
              base_style = BS_CHECKBOX | WS_TABSTOP;
              base_style = BS_CHECKBOX | WS_TABSTOP;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_BUTTON;
              class.u.id = CTL_BUTTON;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | COMBOBOX
        | COMBOBOX
            {
            {
              /* This is as per MSDN documentation.  With some (???)
              /* This is as per MSDN documentation.  With some (???)
                 versions of MS rc.exe their is no default style.  */
                 versions of MS rc.exe their is no default style.  */
              default_style = CBS_SIMPLE | WS_TABSTOP;
              default_style = CBS_SIMPLE | WS_TABSTOP;
              base_style = 0;
              base_style = 0;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_COMBOBOX;
              class.u.id = CTL_COMBOBOX;
              res_text_field = res_null_text;
              res_text_field = res_null_text;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $3;
            $$ = $3;
          }
          }
        | CONTROL optresidc numexpr cresid control_styleexpr cnumexpr
        | CONTROL optresidc numexpr cresid control_styleexpr cnumexpr
            cnumexpr cnumexpr cnumexpr optcnumexpr opt_control_data
            cnumexpr cnumexpr cnumexpr optcnumexpr opt_control_data
          {
          {
            $$ = define_control ($2, $3, $6, $7, $8, $9, $4, style, $10);
            $$ = define_control ($2, $3, $6, $7, $8, $9, $4, style, $10);
            if ($11 != NULL)
            if ($11 != NULL)
              {
              {
                if (dialog.ex == NULL)
                if (dialog.ex == NULL)
                  rcparse_warning (_("control data requires DIALOGEX"));
                  rcparse_warning (_("control data requires DIALOGEX"));
                $$->data = $11;
                $$->data = $11;
              }
              }
          }
          }
        | CONTROL optresidc numexpr cresid control_styleexpr cnumexpr
        | CONTROL optresidc numexpr cresid control_styleexpr cnumexpr
            cnumexpr cnumexpr cnumexpr cnumexpr cnumexpr opt_control_data
            cnumexpr cnumexpr cnumexpr cnumexpr cnumexpr opt_control_data
          {
          {
            $$ = define_control ($2, $3, $6, $7, $8, $9, $4, style, $10);
            $$ = define_control ($2, $3, $6, $7, $8, $9, $4, style, $10);
            if (dialog.ex == NULL)
            if (dialog.ex == NULL)
              rcparse_warning (_("help ID requires DIALOGEX"));
              rcparse_warning (_("help ID requires DIALOGEX"));
            $$->help = $11;
            $$->help = $11;
            $$->data = $12;
            $$->data = $12;
          }
          }
        | CTEXT optresidc
        | CTEXT optresidc
            {
            {
              default_style = SS_CENTER | WS_GROUP;
              default_style = SS_CENTER | WS_GROUP;
              base_style = SS_CENTER;
              base_style = SS_CENTER;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_STATIC;
              class.u.id = CTL_STATIC;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | DEFPUSHBUTTON optresidc
        | DEFPUSHBUTTON optresidc
            {
            {
              default_style = BS_DEFPUSHBUTTON | WS_TABSTOP;
              default_style = BS_DEFPUSHBUTTON | WS_TABSTOP;
              base_style = BS_DEFPUSHBUTTON | WS_TABSTOP;
              base_style = BS_DEFPUSHBUTTON | WS_TABSTOP;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_BUTTON;
              class.u.id = CTL_BUTTON;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | EDITTEXT
        | EDITTEXT
            {
            {
              default_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              default_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              base_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              base_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_EDIT;
              class.u.id = CTL_EDIT;
              res_text_field = res_null_text;
              res_text_field = res_null_text;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $3;
            $$ = $3;
          }
          }
        | GROUPBOX optresidc
        | GROUPBOX optresidc
            {
            {
              default_style = BS_GROUPBOX;
              default_style = BS_GROUPBOX;
              base_style = BS_GROUPBOX;
              base_style = BS_GROUPBOX;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_BUTTON;
              class.u.id = CTL_BUTTON;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | HEDIT optresidc
        | HEDIT optresidc
            {
            {
              default_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              default_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              base_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              base_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_EDIT;
              class.u.id = CTL_EDIT;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
            if (dialog.ex == NULL)
            if (dialog.ex == NULL)
              rcparse_warning (_("IEDIT requires DIALOGEX"));
              rcparse_warning (_("IEDIT requires DIALOGEX"));
            res_string_to_id (&$$->class, "HEDIT");
            res_string_to_id (&$$->class, "HEDIT");
          }
          }
        | ICON resref numexpr cnumexpr cnumexpr opt_control_data
        | ICON resref numexpr cnumexpr cnumexpr opt_control_data
          {
          {
            $$ = define_icon_control ($2, $3, $4, $5, 0, 0, 0, $6,
            $$ = define_icon_control ($2, $3, $4, $5, 0, 0, 0, $6,
                                      dialog.ex);
                                      dialog.ex);
          }
          }
        | ICON resref numexpr cnumexpr cnumexpr cnumexpr cnumexpr
        | ICON resref numexpr cnumexpr cnumexpr cnumexpr cnumexpr
            opt_control_data
            opt_control_data
          {
          {
            $$ = define_icon_control ($2, $3, $4, $5, 0, 0, 0, $8,
            $$ = define_icon_control ($2, $3, $4, $5, 0, 0, 0, $8,
                                      dialog.ex);
                                      dialog.ex);
          }
          }
        | ICON resref numexpr cnumexpr cnumexpr cnumexpr cnumexpr
        | ICON resref numexpr cnumexpr cnumexpr cnumexpr cnumexpr
            icon_styleexpr optcnumexpr opt_control_data
            icon_styleexpr optcnumexpr opt_control_data
          {
          {
            $$ = define_icon_control ($2, $3, $4, $5, style, $9, 0, $10,
            $$ = define_icon_control ($2, $3, $4, $5, style, $9, 0, $10,
                                      dialog.ex);
                                      dialog.ex);
          }
          }
        | ICON resref numexpr cnumexpr cnumexpr cnumexpr cnumexpr
        | ICON resref numexpr cnumexpr cnumexpr cnumexpr cnumexpr
            icon_styleexpr cnumexpr cnumexpr opt_control_data
            icon_styleexpr cnumexpr cnumexpr opt_control_data
          {
          {
            $$ = define_icon_control ($2, $3, $4, $5, style, $9, $10, $11,
            $$ = define_icon_control ($2, $3, $4, $5, style, $9, $10, $11,
                                      dialog.ex);
                                      dialog.ex);
          }
          }
        | IEDIT optresidc
        | IEDIT optresidc
            {
            {
              default_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              default_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              base_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              base_style = ES_LEFT | WS_BORDER | WS_TABSTOP;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_EDIT;
              class.u.id = CTL_EDIT;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
            if (dialog.ex == NULL)
            if (dialog.ex == NULL)
              rcparse_warning (_("IEDIT requires DIALOGEX"));
              rcparse_warning (_("IEDIT requires DIALOGEX"));
            res_string_to_id (&$$->class, "IEDIT");
            res_string_to_id (&$$->class, "IEDIT");
          }
          }
        | LISTBOX
        | LISTBOX
            {
            {
              default_style = LBS_NOTIFY | WS_BORDER;
              default_style = LBS_NOTIFY | WS_BORDER;
              base_style = LBS_NOTIFY | WS_BORDER;
              base_style = LBS_NOTIFY | WS_BORDER;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_LISTBOX;
              class.u.id = CTL_LISTBOX;
              res_text_field = res_null_text;
              res_text_field = res_null_text;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $3;
            $$ = $3;
          }
          }
        | LTEXT optresidc
        | LTEXT optresidc
            {
            {
              default_style = SS_LEFT | WS_GROUP;
              default_style = SS_LEFT | WS_GROUP;
              base_style = SS_LEFT;
              base_style = SS_LEFT;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_STATIC;
              class.u.id = CTL_STATIC;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | PUSHBOX optresidc
        | PUSHBOX optresidc
            {
            {
              default_style = BS_PUSHBOX | WS_TABSTOP;
              default_style = BS_PUSHBOX | WS_TABSTOP;
              base_style = BS_PUSHBOX;
              base_style = BS_PUSHBOX;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_BUTTON;
              class.u.id = CTL_BUTTON;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | PUSHBUTTON optresidc
        | PUSHBUTTON optresidc
            {
            {
              default_style = BS_PUSHBUTTON | WS_TABSTOP;
              default_style = BS_PUSHBUTTON | WS_TABSTOP;
              base_style = BS_PUSHBUTTON | WS_TABSTOP;
              base_style = BS_PUSHBUTTON | WS_TABSTOP;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_BUTTON;
              class.u.id = CTL_BUTTON;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | RADIOBUTTON optresidc
        | RADIOBUTTON optresidc
            {
            {
              default_style = BS_RADIOBUTTON | WS_TABSTOP;
              default_style = BS_RADIOBUTTON | WS_TABSTOP;
              base_style = BS_RADIOBUTTON;
              base_style = BS_RADIOBUTTON;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_BUTTON;
              class.u.id = CTL_BUTTON;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | RTEXT optresidc
        | RTEXT optresidc
            {
            {
              default_style = SS_RIGHT | WS_GROUP;
              default_style = SS_RIGHT | WS_GROUP;
              base_style = SS_RIGHT;
              base_style = SS_RIGHT;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_STATIC;
              class.u.id = CTL_STATIC;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | SCROLLBAR
        | SCROLLBAR
            {
            {
              default_style = SBS_HORZ;
              default_style = SBS_HORZ;
              base_style = 0;
              base_style = 0;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_SCROLLBAR;
              class.u.id = CTL_SCROLLBAR;
              res_text_field = res_null_text;
              res_text_field = res_null_text;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $3;
            $$ = $3;
          }
          }
        | STATE3 optresidc
        | STATE3 optresidc
            {
            {
              default_style = BS_3STATE | WS_TABSTOP;
              default_style = BS_3STATE | WS_TABSTOP;
              base_style = BS_3STATE;
              base_style = BS_3STATE;
              class.named = 0;
              class.named = 0;
              class.u.id = CTL_BUTTON;
              class.u.id = CTL_BUTTON;
              res_text_field = $2;
              res_text_field = $2;
            }
            }
            control_params
            control_params
          {
          {
            $$ = $4;
            $$ = $4;
          }
          }
        | USERBUTTON resref numexpr ',' numexpr ',' numexpr ','
        | USERBUTTON resref numexpr ',' numexpr ',' numexpr ','
            numexpr ',' numexpr ','
            numexpr ',' numexpr ','
            { style = WS_CHILD | WS_VISIBLE; }
            { style = WS_CHILD | WS_VISIBLE; }
            styleexpr optcnumexpr
            styleexpr optcnumexpr
          {
          {
            rc_res_id cid;
            rc_res_id cid;
            cid.named = 0;
            cid.named = 0;
            cid.u.id = CTL_BUTTON;
            cid.u.id = CTL_BUTTON;
            $$ = define_control ($2, $3, $5, $7, $9, $11, cid,
            $$ = define_control ($2, $3, $5, $7, $9, $11, cid,
                                 style, $15);
                                 style, $15);
          }
          }
        ;
        ;
/* Parameters for a control.  The static variables DEFAULT_STYLE,
/* Parameters for a control.  The static variables DEFAULT_STYLE,
   BASE_STYLE, and CLASS must be initialized before this nonterminal
   BASE_STYLE, and CLASS must be initialized before this nonterminal
   is used.  DEFAULT_STYLE is the style to use if no style expression
   is used.  DEFAULT_STYLE is the style to use if no style expression
   is specified.  BASE_STYLE is the base style to use if a style
   is specified.  BASE_STYLE is the base style to use if a style
   expression is specified; the style expression modifies the base
   expression is specified; the style expression modifies the base
   style.  CLASS is the class of the control.  */
   style.  CLASS is the class of the control.  */
control_params:
control_params:
          numexpr cnumexpr cnumexpr cnumexpr cnumexpr opt_control_data
          numexpr cnumexpr cnumexpr cnumexpr cnumexpr opt_control_data
          {
          {
            $$ = define_control (res_text_field, $1, $2, $3, $4, $5, class,
            $$ = define_control (res_text_field, $1, $2, $3, $4, $5, class,
                                 default_style | WS_CHILD | WS_VISIBLE, 0);
                                 default_style | WS_CHILD | WS_VISIBLE, 0);
            if ($6 != NULL)
            if ($6 != NULL)
              {
              {
                if (dialog.ex == NULL)
                if (dialog.ex == NULL)
                  rcparse_warning (_("control data requires DIALOGEX"));
                  rcparse_warning (_("control data requires DIALOGEX"));
                $$->data = $6;
                $$->data = $6;
              }
              }
          }
          }
        | numexpr cnumexpr cnumexpr cnumexpr cnumexpr
        | numexpr cnumexpr cnumexpr cnumexpr cnumexpr
            control_params_styleexpr optcnumexpr opt_control_data
            control_params_styleexpr optcnumexpr opt_control_data
          {
          {
            $$ = define_control (res_text_field, $1, $2, $3, $4, $5, class, style, $7);
            $$ = define_control (res_text_field, $1, $2, $3, $4, $5, class, style, $7);
            if ($8 != NULL)
            if ($8 != NULL)
              {
              {
                if (dialog.ex == NULL)
                if (dialog.ex == NULL)
                  rcparse_warning (_("control data requires DIALOGEX"));
                  rcparse_warning (_("control data requires DIALOGEX"));
                $$->data = $8;
                $$->data = $8;
              }
              }
          }
          }
        | numexpr cnumexpr cnumexpr cnumexpr cnumexpr
        | numexpr cnumexpr cnumexpr cnumexpr cnumexpr
            control_params_styleexpr cnumexpr cnumexpr opt_control_data
            control_params_styleexpr cnumexpr cnumexpr opt_control_data
          {
          {
            $$ = define_control (res_text_field, $1, $2, $3, $4, $5, class, style, $7);
            $$ = define_control (res_text_field, $1, $2, $3, $4, $5, class, style, $7);
            if (dialog.ex == NULL)
            if (dialog.ex == NULL)
              rcparse_warning (_("help ID requires DIALOGEX"));
              rcparse_warning (_("help ID requires DIALOGEX"));
            $$->help = $8;
            $$->help = $8;
            $$->data = $9;
            $$->data = $9;
          }
          }
        ;
        ;
cresid:
cresid:
          ',' resid
          ',' resid
          {
          {
            if ($2.named)
            if ($2.named)
              res_unistring_to_id (&$$, $2.u.n.name);
              res_unistring_to_id (&$$, $2.u.n.name);
            else
            else
              $$=$2;
              $$=$2;
          }
          }
        ;
        ;
optresidc:
optresidc:
          /* empty */
          /* empty */
          {
          {
            res_string_to_id (&$$, "");
            res_string_to_id (&$$, "");
          }
          }
        | resid ',' { $$=$1; }
        | resid ',' { $$=$1; }
        ;
        ;
resid:
resid:
          posnumexpr
          posnumexpr
          {
          {
            $$.named = 0;
            $$.named = 0;
            $$.u.id = $1;
            $$.u.id = $1;
          }
          }
        | res_unicode_string_concat
        | res_unicode_string_concat
          {
          {
            $$.named = 1;
            $$.named = 1;
            $$.u.n.name = $1;
            $$.u.n.name = $1;
            $$.u.n.length = unichar_len ($1);
            $$.u.n.length = unichar_len ($1);
          }
          }
        ;
        ;
opt_control_data:
opt_control_data:
          /* empty */
          /* empty */
          {
          {
            $$ = NULL;
            $$ = NULL;
          }
          }
        | BEG optrcdata_data END
        | BEG optrcdata_data END
          {
          {
            $$ = $2.first;
            $$ = $2.first;
          }
          }
        ;
        ;
/* These only exist to parse a reduction out of a common case.  */
/* These only exist to parse a reduction out of a common case.  */
control_styleexpr:
control_styleexpr:
          ','
          ','
          { style = WS_CHILD | WS_VISIBLE; }
          { style = WS_CHILD | WS_VISIBLE; }
          styleexpr
          styleexpr
        ;
        ;
icon_styleexpr:
icon_styleexpr:
          ','
          ','
          { style = SS_ICON | WS_CHILD | WS_VISIBLE; }
          { style = SS_ICON | WS_CHILD | WS_VISIBLE; }
          styleexpr
          styleexpr
        ;
        ;
control_params_styleexpr:
control_params_styleexpr:
          ','
          ','
          { style = base_style | WS_CHILD | WS_VISIBLE; }
          { style = base_style | WS_CHILD | WS_VISIBLE; }
          styleexpr
          styleexpr
        ;
        ;
/* Font resources.  */
/* Font resources.  */
font:
font:
          id FONT memflags_move_discard file_name
          id FONT memflags_move_discard file_name
          {
          {
            define_font ($1, &$3, $4);
            define_font ($1, &$3, $4);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        ;
        ;
/* Icon resources.  */
/* Icon resources.  */
icon:
icon:
          id ICON memflags_move_discard file_name
          id ICON memflags_move_discard file_name
          {
          {
            define_icon ($1, &$3, $4);
            define_icon ($1, &$3, $4);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        ;
        ;
/* Language command.  This changes the static variable language, which
/* Language command.  This changes the static variable language, which
   affects all subsequent resources.  */
   affects all subsequent resources.  */
language:
language:
          LANGUAGE numexpr cnumexpr
          LANGUAGE numexpr cnumexpr
          {
          {
            language = $2 | ($3 << SUBLANG_SHIFT);
            language = $2 | ($3 << SUBLANG_SHIFT);
          }
          }
        ;
        ;
/* Menu resources.  */
/* Menu resources.  */
menu:
menu:
          id MENU suboptions BEG menuitems END
          id MENU suboptions BEG menuitems END
          {
          {
            define_menu ($1, &$3, $5);
            define_menu ($1, &$3, $5);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        ;
        ;
menuitems:
menuitems:
          /* empty */
          /* empty */
          {
          {
            $$ = NULL;
            $$ = NULL;
          }
          }
        | menuitems menuitem
        | menuitems menuitem
          {
          {
            if ($1 == NULL)
            if ($1 == NULL)
              $$ = $2;
              $$ = $2;
            else
            else
              {
              {
                rc_menuitem **pp;
                rc_menuitem **pp;
                for (pp = &$1->next; *pp != NULL; pp = &(*pp)->next)
                for (pp = &$1->next; *pp != NULL; pp = &(*pp)->next)
                  ;
                  ;
                *pp = $2;
                *pp = $2;
                $$ = $1;
                $$ = $1;
              }
              }
          }
          }
        ;
        ;
menuitem:
menuitem:
          MENUITEM res_unicode_string_concat cnumexpr menuitem_flags
          MENUITEM res_unicode_string_concat cnumexpr menuitem_flags
          {
          {
            $$ = define_menuitem ($2, $3, $4, 0, 0, NULL);
            $$ = define_menuitem ($2, $3, $4, 0, 0, NULL);
          }
          }
        | MENUITEM SEPARATOR
        | MENUITEM SEPARATOR
          {
          {
            $$ = define_menuitem (NULL, 0, 0, 0, 0, NULL);
            $$ = define_menuitem (NULL, 0, 0, 0, 0, NULL);
          }
          }
        | POPUP res_unicode_string_concat menuitem_flags BEG menuitems END
        | POPUP res_unicode_string_concat menuitem_flags BEG menuitems END
          {
          {
            $$ = define_menuitem ($2, 0, $3, 0, 0, $5);
            $$ = define_menuitem ($2, 0, $3, 0, 0, $5);
          }
          }
        ;
        ;
menuitem_flags:
menuitem_flags:
          /* empty */
          /* empty */
          {
          {
            $$ = 0;
            $$ = 0;
          }
          }
        | menuitem_flags ',' menuitem_flag
        | menuitem_flags ',' menuitem_flag
          {
          {
            $$ = $1 | $3;
            $$ = $1 | $3;
          }
          }
        | menuitem_flags menuitem_flag
        | menuitem_flags menuitem_flag
          {
          {
            $$ = $1 | $2;
            $$ = $1 | $2;
          }
          }
        ;
        ;
menuitem_flag:
menuitem_flag:
          CHECKED
          CHECKED
          {
          {
            $$ = MENUITEM_CHECKED;
            $$ = MENUITEM_CHECKED;
          }
          }
        | GRAYED
        | GRAYED
          {
          {
            $$ = MENUITEM_GRAYED;
            $$ = MENUITEM_GRAYED;
          }
          }
        | HELP
        | HELP
          {
          {
            $$ = MENUITEM_HELP;
            $$ = MENUITEM_HELP;
          }
          }
        | INACTIVE
        | INACTIVE
          {
          {
            $$ = MENUITEM_INACTIVE;
            $$ = MENUITEM_INACTIVE;
          }
          }
        | MENUBARBREAK
        | MENUBARBREAK
          {
          {
            $$ = MENUITEM_MENUBARBREAK;
            $$ = MENUITEM_MENUBARBREAK;
          }
          }
        | MENUBREAK
        | MENUBREAK
          {
          {
            $$ = MENUITEM_MENUBREAK;
            $$ = MENUITEM_MENUBREAK;
          }
          }
        ;
        ;
/* Menuex resources.  */
/* Menuex resources.  */
menuex:
menuex:
          id MENUEX suboptions BEG menuexitems END
          id MENUEX suboptions BEG menuexitems END
          {
          {
            define_menu ($1, &$3, $5);
            define_menu ($1, &$3, $5);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        ;
        ;
menuexitems:
menuexitems:
          /* empty */
          /* empty */
          {
          {
            $$ = NULL;
            $$ = NULL;
          }
          }
        | menuexitems menuexitem
        | menuexitems menuexitem
          {
          {
            if ($1 == NULL)
            if ($1 == NULL)
              $$ = $2;
              $$ = $2;
            else
            else
              {
              {
                rc_menuitem **pp;
                rc_menuitem **pp;
                for (pp = &$1->next; *pp != NULL; pp = &(*pp)->next)
                for (pp = &$1->next; *pp != NULL; pp = &(*pp)->next)
                  ;
                  ;
                *pp = $2;
                *pp = $2;
                $$ = $1;
                $$ = $1;
              }
              }
          }
          }
        ;
        ;
menuexitem:
menuexitem:
          MENUITEM res_unicode_string_concat
          MENUITEM res_unicode_string_concat
          {
          {
            $$ = define_menuitem ($2, 0, 0, 0, 0, NULL);
            $$ = define_menuitem ($2, 0, 0, 0, 0, NULL);
          }
          }
        | MENUITEM res_unicode_string_concat cnumexpr
        | MENUITEM res_unicode_string_concat cnumexpr
          {
          {
            $$ = define_menuitem ($2, $3, 0, 0, 0, NULL);
            $$ = define_menuitem ($2, $3, 0, 0, 0, NULL);
          }
          }
        | MENUITEM res_unicode_string_concat cnumexpr cnumexpr optcnumexpr
        | MENUITEM res_unicode_string_concat cnumexpr cnumexpr optcnumexpr
          {
          {
            $$ = define_menuitem ($2, $3, $4, $5, 0, NULL);
            $$ = define_menuitem ($2, $3, $4, $5, 0, NULL);
          }
          }
        | MENUITEM SEPARATOR
        | MENUITEM SEPARATOR
          {
          {
            $$ = define_menuitem (NULL, 0, 0, 0, 0, NULL);
            $$ = define_menuitem (NULL, 0, 0, 0, 0, NULL);
          }
          }
        | POPUP res_unicode_string_concat BEG menuexitems END
        | POPUP res_unicode_string_concat BEG menuexitems END
          {
          {
            $$ = define_menuitem ($2, 0, 0, 0, 0, $4);
            $$ = define_menuitem ($2, 0, 0, 0, 0, $4);
          }
          }
        | POPUP res_unicode_string_concat cnumexpr BEG menuexitems END
        | POPUP res_unicode_string_concat cnumexpr BEG menuexitems END
          {
          {
            $$ = define_menuitem ($2, $3, 0, 0, 0, $5);
            $$ = define_menuitem ($2, $3, 0, 0, 0, $5);
          }
          }
        | POPUP res_unicode_string_concat cnumexpr cnumexpr BEG menuexitems END
        | POPUP res_unicode_string_concat cnumexpr cnumexpr BEG menuexitems END
          {
          {
            $$ = define_menuitem ($2, $3, $4, 0, 0, $6);
            $$ = define_menuitem ($2, $3, $4, 0, 0, $6);
          }
          }
        | POPUP res_unicode_string_concat cnumexpr cnumexpr cnumexpr optcnumexpr
        | POPUP res_unicode_string_concat cnumexpr cnumexpr cnumexpr optcnumexpr
            BEG menuexitems END
            BEG menuexitems END
          {
          {
            $$ = define_menuitem ($2, $3, $4, $5, $6, $8);
            $$ = define_menuitem ($2, $3, $4, $5, $6, $8);
          }
          }
        ;
        ;
/* Messagetable resources.  */
/* Messagetable resources.  */
messagetable:
messagetable:
          id MESSAGETABLE memflags_move file_name
          id MESSAGETABLE memflags_move file_name
          {
          {
            define_messagetable ($1, &$3, $4);
            define_messagetable ($1, &$3, $4);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        ;
        ;
/* We use a different lexing algorithm, because rcdata strings may
/* We use a different lexing algorithm, because rcdata strings may
   contain embedded null bytes, and we need to know the length to use.  */
   contain embedded null bytes, and we need to know the length to use.  */
optrcdata_data:
optrcdata_data:
          {
          {
            rcparse_rcdata ();
            rcparse_rcdata ();
          }
          }
          optrcdata_data_int
          optrcdata_data_int
          {
          {
            rcparse_normal ();
            rcparse_normal ();
            $$ = $2;
            $$ = $2;
          }
          }
        ;
        ;
optrcdata_data_int:
optrcdata_data_int:
          /* empty */
          /* empty */
          {
          {
            $$.first = NULL;
            $$.first = NULL;
            $$.last = NULL;
            $$.last = NULL;
          }
          }
        | rcdata_data
        | rcdata_data
          {
          {
            $$ = $1;
            $$ = $1;
          }
          }
        ;
        ;
rcdata_data:
rcdata_data:
          sizedstring
          sizedstring
          {
          {
            rc_rcdata_item *ri;
            rc_rcdata_item *ri;
            ri = define_rcdata_string ($1.s, $1.length);
            ri = define_rcdata_string ($1.s, $1.length);
            $$.first = ri;
            $$.first = ri;
            $$.last = ri;
            $$.last = ri;
          }
          }
        | sizedunistring
        | sizedunistring
          {
          {
            rc_rcdata_item *ri;
            rc_rcdata_item *ri;
            ri = define_rcdata_unistring ($1.s, $1.length);
            ri = define_rcdata_unistring ($1.s, $1.length);
            $$.first = ri;
            $$.first = ri;
            $$.last = ri;
            $$.last = ri;
          }
          }
        | sizednumexpr
        | sizednumexpr
          {
          {
            rc_rcdata_item *ri;
            rc_rcdata_item *ri;
            ri = define_rcdata_number ($1.val, $1.dword);
            ri = define_rcdata_number ($1.val, $1.dword);
            $$.first = ri;
            $$.first = ri;
            $$.last = ri;
            $$.last = ri;
          }
          }
        | rcdata_data ',' sizedstring
        | rcdata_data ',' sizedstring
          {
          {
            rc_rcdata_item *ri;
            rc_rcdata_item *ri;
            ri = define_rcdata_string ($3.s, $3.length);
            ri = define_rcdata_string ($3.s, $3.length);
            $$.first = $1.first;
            $$.first = $1.first;
            $1.last->next = ri;
            $1.last->next = ri;
            $$.last = ri;
            $$.last = ri;
          }
          }
        | rcdata_data ',' sizedunistring
        | rcdata_data ',' sizedunistring
          {
          {
            rc_rcdata_item *ri;
            rc_rcdata_item *ri;
            ri = define_rcdata_unistring ($3.s, $3.length);
            ri = define_rcdata_unistring ($3.s, $3.length);
            $$.first = $1.first;
            $$.first = $1.first;
            $1.last->next = ri;
            $1.last->next = ri;
            $$.last = ri;
            $$.last = ri;
          }
          }
        | rcdata_data ',' sizednumexpr
        | rcdata_data ',' sizednumexpr
          {
          {
            rc_rcdata_item *ri;
            rc_rcdata_item *ri;
            ri = define_rcdata_number ($3.val, $3.dword);
            ri = define_rcdata_number ($3.val, $3.dword);
            $$.first = $1.first;
            $$.first = $1.first;
            $1.last->next = ri;
            $1.last->next = ri;
            $$.last = ri;
            $$.last = ri;
          }
          }
        ;
        ;
/* Stringtable resources.  */
/* Stringtable resources.  */
stringtable:
stringtable:
          STRINGTABLE suboptions BEG
          STRINGTABLE suboptions BEG
            { sub_res_info = $2; }
            { sub_res_info = $2; }
            string_data END
            string_data END
        ;
        ;
string_data:
string_data:
          /* empty */
          /* empty */
        | string_data numexpr res_unicode_string_concat
        | string_data numexpr res_unicode_string_concat
          {
          {
            define_stringtable (&sub_res_info, $2, $3);
            define_stringtable (&sub_res_info, $2, $3);
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        | string_data numexpr ',' res_unicode_string_concat
        | string_data numexpr ',' res_unicode_string_concat
          {
          {
            define_stringtable (&sub_res_info, $2, $4);
            define_stringtable (&sub_res_info, $2, $4);
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        | string_data error
        | string_data error
          {
          {
            rcparse_warning (_("invalid stringtable resource."));
            rcparse_warning (_("invalid stringtable resource."));
            abort ();
            abort ();
          }
          }
        ;
        ;
rcdata_id:
rcdata_id:
        id
        id
          {
          {
            $$=$1;
            $$=$1;
          }
          }
      | HTML
      | HTML
        {
        {
          $$.named = 0;
          $$.named = 0;
          $$.u.id = 23;
          $$.u.id = 23;
        }
        }
      | RCDATA
      | RCDATA
        {
        {
          $$.named = 0;
          $$.named = 0;
          $$.u.id = RT_RCDATA;
          $$.u.id = RT_RCDATA;
        }
        }
      | MANIFEST
      | MANIFEST
        {
        {
          $$.named = 0;
          $$.named = 0;
          $$.u.id = RT_MANIFEST;
          $$.u.id = RT_MANIFEST;
        }
        }
      | PLUGPLAY
      | PLUGPLAY
        {
        {
          $$.named = 0;
          $$.named = 0;
          $$.u.id = RT_PLUGPLAY;
          $$.u.id = RT_PLUGPLAY;
        }
        }
      | VXD
      | VXD
        {
        {
          $$.named = 0;
          $$.named = 0;
          $$.u.id = RT_VXD;
          $$.u.id = RT_VXD;
        }
        }
      | DLGINCLUDE
      | DLGINCLUDE
        {
        {
          $$.named = 0;
          $$.named = 0;
          $$.u.id = RT_DLGINCLUDE;
          $$.u.id = RT_DLGINCLUDE;
        }
        }
      | DLGINIT
      | DLGINIT
        {
        {
          $$.named = 0;
          $$.named = 0;
          $$.u.id = RT_DLGINIT;
          $$.u.id = RT_DLGINIT;
        }
        }
      | ANICURSOR
      | ANICURSOR
        {
        {
          $$.named = 0;
          $$.named = 0;
          $$.u.id = RT_ANICURSOR;
          $$.u.id = RT_ANICURSOR;
        }
        }
      | ANIICON
      | ANIICON
        {
        {
          $$.named = 0;
          $$.named = 0;
          $$.u.id = RT_ANIICON;
          $$.u.id = RT_ANIICON;
        }
        }
      ;
      ;
/* User defined resources.  We accept general suboptions in the
/* User defined resources.  We accept general suboptions in the
   file_name case to keep the parser happy.  */
   file_name case to keep the parser happy.  */
user:
user:
          id rcdata_id suboptions BEG optrcdata_data END
          id rcdata_id suboptions BEG optrcdata_data END
          {
          {
            define_user_data ($1, $2, &$3, $5.first);
            define_user_data ($1, $2, &$3, $5.first);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        | id rcdata_id suboptions file_name
        | id rcdata_id suboptions file_name
          {
          {
            define_user_file ($1, $2, &$3, $4);
            define_user_file ($1, $2, &$3, $4);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        ;
        ;
toolbar:
toolbar:
        id TOOLBAR suboptions numexpr cnumexpr BEG toolbar_data END
        id TOOLBAR suboptions numexpr cnumexpr BEG toolbar_data END
        {
        {
          define_toolbar ($1, &$3, $4, $5, $7);
          define_toolbar ($1, &$3, $4, $5, $7);
        }
        }
        ;
        ;
toolbar_data: /* empty */ { $$= NULL; }
toolbar_data: /* empty */ { $$= NULL; }
        | toolbar_data BUTTON id
        | toolbar_data BUTTON id
        {
        {
          rc_toolbar_item *c,*n;
          rc_toolbar_item *c,*n;
          c = $1;
          c = $1;
          n= (rc_toolbar_item *)
          n= (rc_toolbar_item *)
              res_alloc (sizeof (rc_toolbar_item));
              res_alloc (sizeof (rc_toolbar_item));
          if (c != NULL)
          if (c != NULL)
            while (c->next != NULL)
            while (c->next != NULL)
              c = c->next;
              c = c->next;
          n->prev = c;
          n->prev = c;
          n->next = NULL;
          n->next = NULL;
          if (c != NULL)
          if (c != NULL)
            c->next = n;
            c->next = n;
          n->id = $3;
          n->id = $3;
          if ($1 == NULL)
          if ($1 == NULL)
            $$ = n;
            $$ = n;
          else
          else
            $$ = $1;
            $$ = $1;
        }
        }
        | toolbar_data SEPARATOR
        | toolbar_data SEPARATOR
        {
        {
          rc_toolbar_item *c,*n;
          rc_toolbar_item *c,*n;
          c = $1;
          c = $1;
          n= (rc_toolbar_item *)
          n= (rc_toolbar_item *)
              res_alloc (sizeof (rc_toolbar_item));
              res_alloc (sizeof (rc_toolbar_item));
          if (c != NULL)
          if (c != NULL)
            while (c->next != NULL)
            while (c->next != NULL)
              c = c->next;
              c = c->next;
          n->prev = c;
          n->prev = c;
          n->next = NULL;
          n->next = NULL;
          if (c != NULL)
          if (c != NULL)
            c->next = n;
            c->next = n;
          n->id.named = 0;
          n->id.named = 0;
          n->id.u.id = 0;
          n->id.u.id = 0;
          if ($1 == NULL)
          if ($1 == NULL)
            $$ = n;
            $$ = n;
          else
          else
            $$ = $1;
            $$ = $1;
        }
        }
        ;
        ;
/* Versioninfo resources.  */
/* Versioninfo resources.  */
versioninfo:
versioninfo:
          id VERSIONINFO fixedverinfo BEG verblocks END
          id VERSIONINFO fixedverinfo BEG verblocks END
          {
          {
            define_versioninfo ($1, language, $3, $5);
            define_versioninfo ($1, language, $3, $5);
            if (yychar != YYEMPTY)
            if (yychar != YYEMPTY)
              YYERROR;
              YYERROR;
            rcparse_discard_strings ();
            rcparse_discard_strings ();
          }
          }
        ;
        ;
fixedverinfo:
fixedverinfo:
          /* empty */
          /* empty */
          {
          {
            $$ = ((rc_fixed_versioninfo *)
            $$ = ((rc_fixed_versioninfo *)
                  res_alloc (sizeof (rc_fixed_versioninfo)));
                  res_alloc (sizeof (rc_fixed_versioninfo)));
            memset ($$, 0, sizeof (rc_fixed_versioninfo));
            memset ($$, 0, sizeof (rc_fixed_versioninfo));
          }
          }
        | fixedverinfo FILEVERSION numexpr cnumexpr cnumexpr cnumexpr
        | fixedverinfo FILEVERSION numexpr cnumexpr cnumexpr cnumexpr
          {
          {
            $1->file_version_ms = ($3 << 16) | $4;
            $1->file_version_ms = ($3 << 16) | $4;
            $1->file_version_ls = ($5 << 16) | $6;
            $1->file_version_ls = ($5 << 16) | $6;
            $$ = $1;
            $$ = $1;
          }
          }
        | fixedverinfo PRODUCTVERSION numexpr cnumexpr cnumexpr cnumexpr
        | fixedverinfo PRODUCTVERSION numexpr cnumexpr cnumexpr cnumexpr
          {
          {
            $1->product_version_ms = ($3 << 16) | $4;
            $1->product_version_ms = ($3 << 16) | $4;
            $1->product_version_ls = ($5 << 16) | $6;
            $1->product_version_ls = ($5 << 16) | $6;
            $$ = $1;
            $$ = $1;
          }
          }
        | fixedverinfo FILEFLAGSMASK numexpr
        | fixedverinfo FILEFLAGSMASK numexpr
          {
          {
            $1->file_flags_mask = $3;
            $1->file_flags_mask = $3;
            $$ = $1;
            $$ = $1;
          }
          }
        | fixedverinfo FILEFLAGS numexpr
        | fixedverinfo FILEFLAGS numexpr
          {
          {
            $1->file_flags = $3;
            $1->file_flags = $3;
            $$ = $1;
            $$ = $1;
          }
          }
        | fixedverinfo FILEOS numexpr
        | fixedverinfo FILEOS numexpr
          {
          {
            $1->file_os = $3;
            $1->file_os = $3;
            $$ = $1;
            $$ = $1;
          }
          }
        | fixedverinfo FILETYPE numexpr
        | fixedverinfo FILETYPE numexpr
          {
          {
            $1->file_type = $3;
            $1->file_type = $3;
            $$ = $1;
            $$ = $1;
          }
          }
        | fixedverinfo FILESUBTYPE numexpr
        | fixedverinfo FILESUBTYPE numexpr
          {
          {
            $1->file_subtype = $3;
            $1->file_subtype = $3;
            $$ = $1;
            $$ = $1;
          }
          }
        ;
        ;
/* To handle verblocks successfully, the lexer handles BLOCK
/* To handle verblocks successfully, the lexer handles BLOCK
   specially.  A BLOCK "StringFileInfo" is returned as
   specially.  A BLOCK "StringFileInfo" is returned as
   BLOCKSTRINGFILEINFO.  A BLOCK "VarFileInfo" is returned as
   BLOCKSTRINGFILEINFO.  A BLOCK "VarFileInfo" is returned as
   BLOCKVARFILEINFO.  A BLOCK with some other string returns BLOCK
   BLOCKVARFILEINFO.  A BLOCK with some other string returns BLOCK
   with the string as the value.  */
   with the string as the value.  */
verblocks:
verblocks:
          /* empty */
          /* empty */
          {
          {
            $$ = NULL;
            $$ = NULL;
          }
          }
        | verblocks BLOCKSTRINGFILEINFO BEG BLOCK BEG vervals END END
        | verblocks BLOCKSTRINGFILEINFO BEG BLOCK BEG vervals END END
          {
          {
            $$ = append_ver_stringfileinfo ($1, $4, $6);
            $$ = append_ver_stringfileinfo ($1, $4, $6);
          }
          }
        | verblocks BLOCKVARFILEINFO BEG VALUE res_unicode_string_concat vertrans END
        | verblocks BLOCKVARFILEINFO BEG VALUE res_unicode_string_concat vertrans END
          {
          {
            $$ = append_ver_varfileinfo ($1, $5, $6);
            $$ = append_ver_varfileinfo ($1, $5, $6);
          }
          }
        ;
        ;
vervals:
vervals:
          /* empty */
          /* empty */
          {
          {
            $$ = NULL;
            $$ = NULL;
          }
          }
        | vervals VALUE res_unicode_string_concat ',' res_unicode_string_concat
        | vervals VALUE res_unicode_string_concat ',' res_unicode_string_concat
          {
          {
            $$ = append_verval ($1, $3, $5);
            $$ = append_verval ($1, $3, $5);
          }
          }
        ;
        ;
vertrans:
vertrans:
          /* empty */
          /* empty */
          {
          {
            $$ = NULL;
            $$ = NULL;
          }
          }
        | vertrans cnumexpr cnumexpr
        | vertrans cnumexpr cnumexpr
          {
          {
            $$ = append_vertrans ($1, $2, $3);
            $$ = append_vertrans ($1, $2, $3);
          }
          }
        ;
        ;
/* A resource ID.  */
/* A resource ID.  */
id:
id:
          posnumexpr
          posnumexpr
          {
          {
            $$.named = 0;
            $$.named = 0;
            $$.u.id = $1;
            $$.u.id = $1;
          }
          }
        | resname
        | resname
          {
          {
            res_unistring_to_id (&$$, $1);
            res_unistring_to_id (&$$, $1);
          }
          }
        ;
        ;
/* A resource reference.  */
/* A resource reference.  */
resname:
resname:
          res_unicode_string
          res_unicode_string
          {
          {
            $$ = $1;
            $$ = $1;
          }
          }
        | STRING
        | STRING
          {
          {
            unichar *h = NULL;
            unichar *h = NULL;
            unicode_from_ascii ((rc_uint_type *) NULL, &h, $1);
            unicode_from_ascii ((rc_uint_type *) NULL, &h, $1);
            $$ = h;
            $$ = h;
          }
          }
        ;
        ;
resref:
resref:
          posnumexpr ','
          posnumexpr ','
          {
          {
            $$.named = 0;
            $$.named = 0;
            $$.u.id = $1;
            $$.u.id = $1;
          }
          }
        | resname
        | resname
          {
          {
            res_unistring_to_id (&$$, $1);
            res_unistring_to_id (&$$, $1);
          }
          }
        | resname ','
        | resname ','
          {
          {
            res_unistring_to_id (&$$, $1);
            res_unistring_to_id (&$$, $1);
          }
          }
        ;
        ;
/* Generic suboptions.  These may appear before the BEGIN in any
/* Generic suboptions.  These may appear before the BEGIN in any
   multiline statement.  */
   multiline statement.  */
suboptions:
suboptions:
          /* empty */
          /* empty */
          {
          {
            memset (&$$, 0, sizeof (rc_res_res_info));
            memset (&$$, 0, sizeof (rc_res_res_info));
            $$.language = language;
            $$.language = language;
            /* FIXME: Is this the right default?  */
            /* FIXME: Is this the right default?  */
            $$.memflags = MEMFLAG_MOVEABLE | MEMFLAG_PURE | MEMFLAG_DISCARDABLE;
            $$.memflags = MEMFLAG_MOVEABLE | MEMFLAG_PURE | MEMFLAG_DISCARDABLE;
          }
          }
        | suboptions memflag
        | suboptions memflag
          {
          {
            $$ = $1;
            $$ = $1;
            $$.memflags |= $2.on;
            $$.memflags |= $2.on;
            $$.memflags &=~ $2.off;
            $$.memflags &=~ $2.off;
          }
          }
        | suboptions CHARACTERISTICS numexpr
        | suboptions CHARACTERISTICS numexpr
          {
          {
            $$ = $1;
            $$ = $1;
            $$.characteristics = $3;
            $$.characteristics = $3;
          }
          }
        | suboptions LANGUAGE numexpr cnumexpr
        | suboptions LANGUAGE numexpr cnumexpr
          {
          {
            $$ = $1;
            $$ = $1;
            $$.language = $3 | ($4 << SUBLANG_SHIFT);
            $$.language = $3 | ($4 << SUBLANG_SHIFT);
          }
          }
        | suboptions VERSIONK numexpr
        | suboptions VERSIONK numexpr
          {
          {
            $$ = $1;
            $$ = $1;
            $$.version = $3;
            $$.version = $3;
          }
          }
        ;
        ;
/* Memory flags which default to MOVEABLE and DISCARDABLE.  */
/* Memory flags which default to MOVEABLE and DISCARDABLE.  */
memflags_move_discard:
memflags_move_discard:
          /* empty */
          /* empty */
          {
          {
            memset (&$$, 0, sizeof (rc_res_res_info));
            memset (&$$, 0, sizeof (rc_res_res_info));
            $$.language = language;
            $$.language = language;
            $$.memflags = MEMFLAG_MOVEABLE | MEMFLAG_DISCARDABLE;
            $$.memflags = MEMFLAG_MOVEABLE | MEMFLAG_DISCARDABLE;
          }
          }
        | memflags_move_discard memflag
        | memflags_move_discard memflag
          {
          {
            $$ = $1;
            $$ = $1;
            $$.memflags |= $2.on;
            $$.memflags |= $2.on;
            $$.memflags &=~ $2.off;
            $$.memflags &=~ $2.off;
          }
          }
        ;
        ;
/* Memory flags which default to MOVEABLE.  */
/* Memory flags which default to MOVEABLE.  */
memflags_move:
memflags_move:
          /* empty */
          /* empty */
          {
          {
            memset (&$$, 0, sizeof (rc_res_res_info));
            memset (&$$, 0, sizeof (rc_res_res_info));
            $$.language = language;
            $$.language = language;
            $$.memflags = MEMFLAG_MOVEABLE | MEMFLAG_PURE | MEMFLAG_DISCARDABLE;
            $$.memflags = MEMFLAG_MOVEABLE | MEMFLAG_PURE | MEMFLAG_DISCARDABLE;
          }
          }
        | memflags_move memflag
        | memflags_move memflag
          {
          {
            $$ = $1;
            $$ = $1;
            $$.memflags |= $2.on;
            $$.memflags |= $2.on;
            $$.memflags &=~ $2.off;
            $$.memflags &=~ $2.off;
          }
          }
        ;
        ;
/* Memory flags.  This returns a struct with two integers, because we
/* Memory flags.  This returns a struct with two integers, because we
   sometimes want to set bits and we sometimes want to clear them.  */
   sometimes want to set bits and we sometimes want to clear them.  */
memflag:
memflag:
          MOVEABLE
          MOVEABLE
          {
          {
            $$.on = MEMFLAG_MOVEABLE;
            $$.on = MEMFLAG_MOVEABLE;
            $$.off = 0;
            $$.off = 0;
          }
          }
        | FIXED
        | FIXED
          {
          {
            $$.on = 0;
            $$.on = 0;
            $$.off = MEMFLAG_MOVEABLE;
            $$.off = MEMFLAG_MOVEABLE;
          }
          }
        | PURE
        | PURE
          {
          {
            $$.on = MEMFLAG_PURE;
            $$.on = MEMFLAG_PURE;
            $$.off = 0;
            $$.off = 0;
          }
          }
        | IMPURE
        | IMPURE
          {
          {
            $$.on = 0;
            $$.on = 0;
            $$.off = MEMFLAG_PURE;
            $$.off = MEMFLAG_PURE;
          }
          }
        | PRELOAD
        | PRELOAD
          {
          {
            $$.on = MEMFLAG_PRELOAD;
            $$.on = MEMFLAG_PRELOAD;
            $$.off = 0;
            $$.off = 0;
          }
          }
        | LOADONCALL
        | LOADONCALL
          {
          {
            $$.on = 0;
            $$.on = 0;
            $$.off = MEMFLAG_PRELOAD;
            $$.off = MEMFLAG_PRELOAD;
          }
          }
        | DISCARDABLE
        | DISCARDABLE
          {
          {
            $$.on = MEMFLAG_DISCARDABLE;
            $$.on = MEMFLAG_DISCARDABLE;
            $$.off = 0;
            $$.off = 0;
          }
          }
        ;
        ;
/* A file name.  */
/* A file name.  */
file_name:
file_name:
          QUOTEDSTRING
          QUOTEDSTRING
          {
          {
            $$ = $1;
            $$ = $1;
          }
          }
        | STRING
        | STRING
          {
          {
            $$ = $1;
            $$ = $1;
          }
          }
        ;
        ;
/* Concat string */
/* Concat string */
res_unicode_string_concat:
res_unicode_string_concat:
          res_unicode_string
          res_unicode_string
          {
          {
            $$ = $1;
            $$ = $1;
          }
          }
        |
        |
          res_unicode_string_concat res_unicode_string
          res_unicode_string_concat res_unicode_string
          {
          {
            rc_uint_type l1 = unichar_len ($1);
            rc_uint_type l1 = unichar_len ($1);
            rc_uint_type l2 = unichar_len ($2);
            rc_uint_type l2 = unichar_len ($2);
            unichar *h = (unichar *) res_alloc ((l1 + l2 + 1) * sizeof (unichar));
            unichar *h = (unichar *) res_alloc ((l1 + l2 + 1) * sizeof (unichar));
            if (l1 != 0)
            if (l1 != 0)
              memcpy (h, $1, l1 * sizeof (unichar));
              memcpy (h, $1, l1 * sizeof (unichar));
            if (l2 != 0)
            if (l2 != 0)
              memcpy (h + l1, $2, l2  * sizeof (unichar));
              memcpy (h + l1, $2, l2  * sizeof (unichar));
            h[l1 + l2] = 0;
            h[l1 + l2] = 0;
            $$ = h;
            $$ = h;
          }
          }
        ;
        ;
res_unicode_string:
res_unicode_string:
          QUOTEDUNISTRING
          QUOTEDUNISTRING
          {
          {
            $$ = unichar_dup ($1);
            $$ = unichar_dup ($1);
          }
          }
        | QUOTEDSTRING
        | QUOTEDSTRING
          {
          {
            unichar *h = NULL;
            unichar *h = NULL;
            unicode_from_ascii ((rc_uint_type *) NULL, &h, $1);
            unicode_from_ascii ((rc_uint_type *) NULL, &h, $1);
            $$ = h;
            $$ = h;
          }
          }
        ;
        ;
sizedstring:
sizedstring:
          SIZEDSTRING
          SIZEDSTRING
          {
          {
            $$ = $1;
            $$ = $1;
          }
          }
        | sizedstring SIZEDSTRING
        | sizedstring SIZEDSTRING
          {
          {
            rc_uint_type l = $1.length + $2.length;
            rc_uint_type l = $1.length + $2.length;
            char *h = (char *) res_alloc (l);
            char *h = (char *) res_alloc (l);
            memcpy (h, $1.s, $1.length);
            memcpy (h, $1.s, $1.length);
            memcpy (h + $1.length, $2.s, $2.length);
            memcpy (h + $1.length, $2.s, $2.length);
            $$.s = h;
            $$.s = h;
            $$.length = l;
            $$.length = l;
          }
          }
        ;
        ;
sizedunistring:
sizedunistring:
          SIZEDUNISTRING
          SIZEDUNISTRING
          {
          {
            $$ = $1;
            $$ = $1;
          }
          }
        | sizedunistring SIZEDUNISTRING
        | sizedunistring SIZEDUNISTRING
          {
          {
            rc_uint_type l = $1.length + $2.length;
            rc_uint_type l = $1.length + $2.length;
            unichar *h = (unichar *) res_alloc (l * sizeof (unichar));
            unichar *h = (unichar *) res_alloc (l * sizeof (unichar));
            memcpy (h, $1.s, $1.length * sizeof (unichar));
            memcpy (h, $1.s, $1.length * sizeof (unichar));
            memcpy (h + $1.length, $2.s, $2.length  * sizeof (unichar));
            memcpy (h + $1.length, $2.s, $2.length  * sizeof (unichar));
            $$.s = h;
            $$.s = h;
            $$.length = l;
            $$.length = l;
          }
          }
        ;
        ;
/* A style expression.  This changes the static variable STYLE.  We do
/* A style expression.  This changes the static variable STYLE.  We do
   it this way because rc appears to permit a style to be set to
   it this way because rc appears to permit a style to be set to
   something like
   something like
       WS_GROUP | NOT WS_TABSTOP
       WS_GROUP | NOT WS_TABSTOP
   to mean that a default of WS_TABSTOP should be removed.  Anything
   to mean that a default of WS_TABSTOP should be removed.  Anything
   which wants to accept a style must first set STYLE to the default
   which wants to accept a style must first set STYLE to the default
   value.  The styleexpr nonterminal will change STYLE as specified by
   value.  The styleexpr nonterminal will change STYLE as specified by
   the user.  Note that we do not accept arbitrary expressions here,
   the user.  Note that we do not accept arbitrary expressions here,
   just numbers separated by '|'.  */
   just numbers separated by '|'.  */
styleexpr:
styleexpr:
          parennumber
          parennumber
          {
          {
            style |= $1;
            style |= $1;
          }
          }
        | NOT parennumber
        | NOT parennumber
          {
          {
            style &=~ $2;
            style &=~ $2;
          }
          }
        | styleexpr '|' parennumber
        | styleexpr '|' parennumber
          {
          {
            style |= $3;
            style |= $3;
          }
          }
        | styleexpr '|' NOT parennumber
        | styleexpr '|' NOT parennumber
          {
          {
            style &=~ $4;
            style &=~ $4;
          }
          }
        ;
        ;
parennumber:
parennumber:
          NUMBER
          NUMBER
          {
          {
            $$ = $1.val;
            $$ = $1.val;
          }
          }
        | '(' numexpr ')'
        | '(' numexpr ')'
          {
          {
            $$ = $2;
            $$ = $2;
          }
          }
        ;
        ;
/* An optional expression with a leading comma.  */
/* An optional expression with a leading comma.  */
optcnumexpr:
optcnumexpr:
          /* empty */
          /* empty */
          {
          {
            $$ = 0;
            $$ = 0;
          }
          }
        | cnumexpr
        | cnumexpr
          {
          {
            $$ = $1;
            $$ = $1;
          }
          }
        ;
        ;
/* An expression with a leading comma.  */
/* An expression with a leading comma.  */
cnumexpr:
cnumexpr:
          ',' numexpr
          ',' numexpr
          {
          {
            $$ = $2;
            $$ = $2;
          }
          }
        ;
        ;
/* A possibly negated numeric expression.  */
/* A possibly negated numeric expression.  */
numexpr:
numexpr:
          sizednumexpr
          sizednumexpr
          {
          {
            $$ = $1.val;
            $$ = $1.val;
          }
          }
        ;
        ;
/* A possibly negated expression with a size.  */
/* A possibly negated expression with a size.  */
sizednumexpr:
sizednumexpr:
          NUMBER
          NUMBER
          {
          {
            $$ = $1;
            $$ = $1;
          }
          }
        | '(' sizednumexpr ')'
        | '(' sizednumexpr ')'
          {
          {
            $$ = $2;
            $$ = $2;
          }
          }
        | '~' sizednumexpr %prec '~'
        | '~' sizednumexpr %prec '~'
          {
          {
            $$.val = ~ $2.val;
            $$.val = ~ $2.val;
            $$.dword = $2.dword;
            $$.dword = $2.dword;
          }
          }
        | '-' sizednumexpr %prec NEG
        | '-' sizednumexpr %prec NEG
          {
          {
            $$.val = - $2.val;
            $$.val = - $2.val;
            $$.dword = $2.dword;
            $$.dword = $2.dword;
          }
          }
        | sizednumexpr '*' sizednumexpr
        | sizednumexpr '*' sizednumexpr
          {
          {
            $$.val = $1.val * $3.val;
            $$.val = $1.val * $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizednumexpr '/' sizednumexpr
        | sizednumexpr '/' sizednumexpr
          {
          {
            $$.val = $1.val / $3.val;
            $$.val = $1.val / $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizednumexpr '%' sizednumexpr
        | sizednumexpr '%' sizednumexpr
          {
          {
            $$.val = $1.val % $3.val;
            $$.val = $1.val % $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizednumexpr '+' sizednumexpr
        | sizednumexpr '+' sizednumexpr
          {
          {
            $$.val = $1.val + $3.val;
            $$.val = $1.val + $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizednumexpr '-' sizednumexpr
        | sizednumexpr '-' sizednumexpr
          {
          {
            $$.val = $1.val - $3.val;
            $$.val = $1.val - $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizednumexpr '&' sizednumexpr
        | sizednumexpr '&' sizednumexpr
          {
          {
            $$.val = $1.val & $3.val;
            $$.val = $1.val & $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizednumexpr '^' sizednumexpr
        | sizednumexpr '^' sizednumexpr
          {
          {
            $$.val = $1.val ^ $3.val;
            $$.val = $1.val ^ $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizednumexpr '|' sizednumexpr
        | sizednumexpr '|' sizednumexpr
          {
          {
            $$.val = $1.val | $3.val;
            $$.val = $1.val | $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        ;
        ;
/* An expression with a leading comma which does not use unary
/* An expression with a leading comma which does not use unary
   negation.  */
   negation.  */
cposnumexpr:
cposnumexpr:
          ',' posnumexpr
          ',' posnumexpr
          {
          {
            $$ = $2;
            $$ = $2;
          }
          }
        ;
        ;
/* An expression which does not use unary negation.  */
/* An expression which does not use unary negation.  */
posnumexpr:
posnumexpr:
          sizedposnumexpr
          sizedposnumexpr
          {
          {
            $$ = $1.val;
            $$ = $1.val;
          }
          }
        ;
        ;
/* An expression which does not use unary negation.  We separate unary
/* An expression which does not use unary negation.  We separate unary
   negation to avoid parsing conflicts when two numeric expressions
   negation to avoid parsing conflicts when two numeric expressions
   appear consecutively.  */
   appear consecutively.  */
sizedposnumexpr:
sizedposnumexpr:
          NUMBER
          NUMBER
          {
          {
            $$ = $1;
            $$ = $1;
          }
          }
        | '(' sizednumexpr ')'
        | '(' sizednumexpr ')'
          {
          {
            $$ = $2;
            $$ = $2;
          }
          }
        | '~' sizednumexpr %prec '~'
        | '~' sizednumexpr %prec '~'
          {
          {
            $$.val = ~ $2.val;
            $$.val = ~ $2.val;
            $$.dword = $2.dword;
            $$.dword = $2.dword;
          }
          }
        | sizedposnumexpr '*' sizednumexpr
        | sizedposnumexpr '*' sizednumexpr
          {
          {
            $$.val = $1.val * $3.val;
            $$.val = $1.val * $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizedposnumexpr '/' sizednumexpr
        | sizedposnumexpr '/' sizednumexpr
          {
          {
            $$.val = $1.val / $3.val;
            $$.val = $1.val / $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizedposnumexpr '%' sizednumexpr
        | sizedposnumexpr '%' sizednumexpr
          {
          {
            $$.val = $1.val % $3.val;
            $$.val = $1.val % $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizedposnumexpr '+' sizednumexpr
        | sizedposnumexpr '+' sizednumexpr
          {
          {
            $$.val = $1.val + $3.val;
            $$.val = $1.val + $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizedposnumexpr '-' sizednumexpr
        | sizedposnumexpr '-' sizednumexpr
          {
          {
            $$.val = $1.val - $3.val;
            $$.val = $1.val - $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizedposnumexpr '&' sizednumexpr
        | sizedposnumexpr '&' sizednumexpr
          {
          {
            $$.val = $1.val & $3.val;
            $$.val = $1.val & $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizedposnumexpr '^' sizednumexpr
        | sizedposnumexpr '^' sizednumexpr
          {
          {
            $$.val = $1.val ^ $3.val;
            $$.val = $1.val ^ $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        | sizedposnumexpr '|' sizednumexpr
        | sizedposnumexpr '|' sizednumexpr
          {
          {
            $$.val = $1.val | $3.val;
            $$.val = $1.val | $3.val;
            $$.dword = $1.dword || $3.dword;
            $$.dword = $1.dword || $3.dword;
          }
          }
        ;
        ;
%%
%%
/* Set the language from the command line.  */
/* Set the language from the command line.  */
void
void
rcparse_set_language (int lang)
rcparse_set_language (int lang)
{
{
  language = lang;
  language = lang;
}
}
 
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.