Home | History | Annotate | Download | only in ld
      1 /* A YACC grammar to parse a superset of the AT&T linker scripting language.
      2    Copyright (C) 1991-2016 Free Software Foundation, Inc.
      3    Written by Steve Chamberlain of Cygnus Support (steve (at) cygnus.com).
      4 
      5    This file is part of the GNU Binutils.
      6 
      7    This program is free software; you can redistribute it and/or modify
      8    it under the terms of the GNU General Public License as published by
      9    the Free Software Foundation; either version 3 of the License, or
     10    (at your option) any later version.
     11 
     12    This program is distributed in the hope that it will be useful,
     13    but WITHOUT ANY WARRANTY; without even the implied warranty of
     14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     15    GNU General Public License for more details.
     16 
     17    You should have received a copy of the GNU General Public License
     18    along with this program; if not, write to the Free Software
     19    Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
     20    MA 02110-1301, USA.  */
     21 
     22 %{
     23 /*
     24 
     25  */
     26 
     27 #define DONTDECLARE_MALLOC
     28 
     29 #include "sysdep.h"
     30 #include "bfd.h"
     31 #include "bfdlink.h"
     32 #include "ld.h"
     33 #include "ldexp.h"
     34 #include "ldver.h"
     35 #include "ldlang.h"
     36 #include "ldfile.h"
     37 #include "ldemul.h"
     38 #include "ldmisc.h"
     39 #include "ldmain.h"
     40 #include "mri.h"
     41 #include "ldctor.h"
     42 #include "ldlex.h"
     43 
     44 #ifndef YYDEBUG
     45 #define YYDEBUG 1
     46 #endif
     47 
     48 static enum section_type sectype;
     49 static lang_memory_region_type *region;
     50 
     51 bfd_boolean ldgram_had_keep = FALSE;
     52 char *ldgram_vers_current_lang = NULL;
     53 
     54 #define ERROR_NAME_MAX 20
     55 static char *error_names[ERROR_NAME_MAX];
     56 static int error_index;
     57 #define PUSH_ERROR(x) if (error_index < ERROR_NAME_MAX) error_names[error_index] = x; error_index++;
     58 #define POP_ERROR()   error_index--;
     59 %}
     60 %union {
     61   bfd_vma integer;
     62   struct big_int
     63     {
     64       bfd_vma integer;
     65       char *str;
     66     } bigint;
     67   fill_type *fill;
     68   char *name;
     69   const char *cname;
     70   struct wildcard_spec wildcard;
     71   struct wildcard_list *wildcard_list;
     72   struct name_list *name_list;
     73   struct flag_info_list *flag_info_list;
     74   struct flag_info *flag_info;
     75   int token;
     76   union etree_union *etree;
     77   struct phdr_info
     78     {
     79       bfd_boolean filehdr;
     80       bfd_boolean phdrs;
     81       union etree_union *at;
     82       union etree_union *flags;
     83     } phdr;
     84   struct lang_nocrossref *nocrossref;
     85   struct lang_output_section_phdr_list *section_phdr;
     86   struct bfd_elf_version_deps *deflist;
     87   struct bfd_elf_version_expr *versyms;
     88   struct bfd_elf_version_tree *versnode;
     89 }
     90 
     91 %type <etree> exp opt_exp_with_type mustbe_exp opt_at phdr_type phdr_val
     92 %type <etree> opt_exp_without_type opt_subalign opt_align
     93 %type <fill> fill_opt fill_exp
     94 %type <name_list> exclude_name_list
     95 %type <wildcard_list> file_NAME_list
     96 %type <flag_info_list> sect_flag_list
     97 %type <flag_info> sect_flags
     98 %type <name> memspec_opt casesymlist
     99 %type <name> memspec_at_opt
    100 %type <cname> wildcard_name
    101 %type <wildcard> wildcard_spec
    102 %token <bigint> INT
    103 %token <name> NAME LNAME
    104 %type <integer> length
    105 %type <phdr> phdr_qualifiers
    106 %type <nocrossref> nocrossref_list
    107 %type <section_phdr> phdr_opt
    108 %type <integer> opt_nocrossrefs
    109 
    110 %right <token> PLUSEQ MINUSEQ MULTEQ DIVEQ  '=' LSHIFTEQ RSHIFTEQ   ANDEQ OREQ
    111 %right <token> '?' ':'
    112 %left <token> OROR
    113 %left <token>  ANDAND
    114 %left <token> '|'
    115 %left <token>  '^'
    116 %left  <token> '&'
    117 %left <token>  EQ NE
    118 %left  <token> '<' '>' LE GE
    119 %left  <token> LSHIFT RSHIFT
    120 
    121 %left  <token> '+' '-'
    122 %left  <token> '*' '/' '%'
    123 
    124 %right UNARY
    125 %token END
    126 %left <token> '('
    127 %token <token> ALIGN_K BLOCK BIND QUAD SQUAD LONG SHORT BYTE
    128 %token SECTIONS PHDRS INSERT_K AFTER BEFORE
    129 %token DATA_SEGMENT_ALIGN DATA_SEGMENT_RELRO_END DATA_SEGMENT_END
    130 %token SORT_BY_NAME SORT_BY_ALIGNMENT SORT_NONE
    131 %token SORT_BY_INIT_PRIORITY
    132 %token '{' '}'
    133 %token SIZEOF_HEADERS OUTPUT_FORMAT FORCE_COMMON_ALLOCATION OUTPUT_ARCH
    134 %token INHIBIT_COMMON_ALLOCATION
    135 %token SEGMENT_START
    136 %token INCLUDE
    137 %token MEMORY
    138 %token REGION_ALIAS
    139 %token LD_FEATURE
    140 %token NOLOAD DSECT COPY INFO OVERLAY
    141 %token DEFINED TARGET_K SEARCH_DIR MAP ENTRY
    142 %token <integer> NEXT
    143 %token SIZEOF ALIGNOF ADDR LOADADDR MAX_K MIN_K
    144 %token STARTUP HLL SYSLIB FLOAT NOFLOAT NOCROSSREFS NOCROSSREFS_TO
    145 %token ORIGIN FILL
    146 %token LENGTH CREATE_OBJECT_SYMBOLS INPUT GROUP OUTPUT CONSTRUCTORS
    147 %token ALIGNMOD AT SUBALIGN HIDDEN PROVIDE PROVIDE_HIDDEN AS_NEEDED
    148 %type <token> assign_op atype attributes_opt sect_constraint opt_align_with_input
    149 %type <name>  filename
    150 %token CHIP LIST SECT ABSOLUTE  LOAD NEWLINE ENDWORD ORDER NAMEWORD ASSERT_K
    151 %token LOG2CEIL FORMAT PUBLIC DEFSYMEND BASE ALIAS TRUNCATE REL
    152 %token INPUT_SCRIPT INPUT_MRI_SCRIPT INPUT_DEFSYM CASE EXTERN START
    153 %token <name> VERS_TAG VERS_IDENTIFIER
    154 %token GLOBAL LOCAL VERSIONK INPUT_VERSION_SCRIPT
    155 %token KEEP ONLY_IF_RO ONLY_IF_RW SPECIAL INPUT_SECTION_FLAGS ALIGN_WITH_INPUT
    156 %token EXCLUDE_FILE
    157 %token CONSTANT
    158 %type <versyms> vers_defns
    159 %type <versnode> vers_tag
    160 %type <deflist> verdep
    161 %token INPUT_DYNAMIC_LIST
    162 
    163 %%
    164 
    165 file:
    166 		INPUT_SCRIPT script_file
    167 	|	INPUT_MRI_SCRIPT mri_script_file
    168 	|	INPUT_VERSION_SCRIPT version_script_file
    169 	|	INPUT_DYNAMIC_LIST dynamic_list_file
    170 	|	INPUT_DEFSYM defsym_expr
    171 	;
    172 
    173 
    174 filename:  NAME;
    175 
    176 
    177 defsym_expr:
    178 		{ ldlex_defsym(); }
    179 		NAME '=' exp
    180 		{
    181 		  ldlex_popstate();
    182 		  lang_add_assignment (exp_defsym ($2, $4));
    183 		}
    184 	;
    185 
    186 /* SYNTAX WITHIN AN MRI SCRIPT FILE */
    187 mri_script_file:
    188 		{
    189 		  ldlex_mri_script ();
    190 		  PUSH_ERROR (_("MRI style script"));
    191 		}
    192 	     mri_script_lines
    193 		{
    194 		  ldlex_popstate ();
    195 		  mri_draw_tree ();
    196 		  POP_ERROR ();
    197 		}
    198 	;
    199 
    200 mri_script_lines:
    201 		mri_script_lines mri_script_command NEWLINE
    202           |
    203 	;
    204 
    205 mri_script_command:
    206 		CHIP  exp
    207 	|	CHIP  exp ',' exp
    208 	|	NAME 	{
    209 			einfo(_("%P%F: unrecognised keyword in MRI style script '%s'\n"),$1);
    210 			}
    211 	|	LIST  	{
    212 			config.map_filename = "-";
    213 			}
    214         |       ORDER ordernamelist
    215 	|       ENDWORD
    216         |       PUBLIC NAME '=' exp
    217  			{ mri_public($2, $4); }
    218         |       PUBLIC NAME ',' exp
    219  			{ mri_public($2, $4); }
    220         |       PUBLIC NAME  exp
    221  			{ mri_public($2, $3); }
    222 	| 	FORMAT NAME
    223 			{ mri_format($2); }
    224 	|	SECT NAME ',' exp
    225 			{ mri_output_section($2, $4);}
    226 	|	SECT NAME  exp
    227 			{ mri_output_section($2, $3);}
    228 	|	SECT NAME '=' exp
    229 			{ mri_output_section($2, $4);}
    230 	|	ALIGN_K NAME '=' exp
    231 			{ mri_align($2,$4); }
    232 	|	ALIGN_K NAME ',' exp
    233 			{ mri_align($2,$4); }
    234 	|	ALIGNMOD NAME '=' exp
    235 			{ mri_alignmod($2,$4); }
    236 	|	ALIGNMOD NAME ',' exp
    237 			{ mri_alignmod($2,$4); }
    238 	|	ABSOLUTE mri_abs_name_list
    239 	|	LOAD	 mri_load_name_list
    240 	|       NAMEWORD NAME
    241 			{ mri_name($2); }
    242 	|	ALIAS NAME ',' NAME
    243 			{ mri_alias($2,$4,0);}
    244 	|	ALIAS NAME ',' INT
    245 			{ mri_alias ($2, 0, (int) $4.integer); }
    246 	|	BASE     exp
    247 			{ mri_base($2); }
    248 	|	TRUNCATE INT
    249 		{ mri_truncate ((unsigned int) $2.integer); }
    250 	|	CASE casesymlist
    251 	|	EXTERN extern_name_list
    252 	|	INCLUDE filename
    253 		{ ldlex_script (); ldfile_open_command_file($2); }
    254 		mri_script_lines END
    255 		{ ldlex_popstate (); }
    256 	|	START NAME
    257 		{ lang_add_entry ($2, FALSE); }
    258         |
    259 	;
    260 
    261 ordernamelist:
    262 	      ordernamelist ',' NAME         { mri_order($3); }
    263 	|     ordernamelist  NAME         { mri_order($2); }
    264       	|
    265 	;
    266 
    267 mri_load_name_list:
    268 		NAME
    269 			{ mri_load($1); }
    270 	|	mri_load_name_list ',' NAME { mri_load($3); }
    271 	;
    272 
    273 mri_abs_name_list:
    274  		NAME
    275  			{ mri_only_load($1); }
    276 	|	mri_abs_name_list ','  NAME
    277  			{ mri_only_load($3); }
    278 	;
    279 
    280 casesymlist:
    281 	  /* empty */ { $$ = NULL; }
    282 	| NAME
    283 	| casesymlist ',' NAME
    284 	;
    285 
    286 /* Parsed as expressions so that commas separate entries */
    287 extern_name_list:
    288 	{ ldlex_expression (); }
    289 	extern_name_list_body
    290 	{ ldlex_popstate (); }
    291 
    292 extern_name_list_body:
    293 	  NAME
    294 			{ ldlang_add_undef ($1, FALSE); }
    295 	| extern_name_list_body NAME
    296 			{ ldlang_add_undef ($2, FALSE); }
    297 	| extern_name_list_body ',' NAME
    298 			{ ldlang_add_undef ($3, FALSE); }
    299 	;
    300 
    301 script_file:
    302 	{ ldlex_both(); }
    303 	ifile_list
    304 	{ ldlex_popstate(); }
    305         ;
    306 
    307 ifile_list:
    308 	ifile_list ifile_p1
    309         |
    310 	;
    311 
    312 
    313 ifile_p1:
    314 		memory
    315 	|	sections
    316 	|	phdrs
    317 	|	startup
    318 	|	high_level_library
    319 	|	low_level_library
    320 	|	floating_point_support
    321 	|	statement_anywhere
    322 	|	version
    323         |	 ';'
    324 	|	TARGET_K '(' NAME ')'
    325 		{ lang_add_target($3); }
    326 	|	SEARCH_DIR '(' filename ')'
    327 		{ ldfile_add_library_path ($3, FALSE); }
    328 	|	OUTPUT '(' filename ')'
    329 		{ lang_add_output($3, 1); }
    330         |	OUTPUT_FORMAT '(' NAME ')'
    331 		  { lang_add_output_format ($3, (char *) NULL,
    332 					    (char *) NULL, 1); }
    333 	|	OUTPUT_FORMAT '(' NAME ',' NAME ',' NAME ')'
    334 		  { lang_add_output_format ($3, $5, $7, 1); }
    335         |	OUTPUT_ARCH '(' NAME ')'
    336 		  { ldfile_set_output_arch ($3, bfd_arch_unknown); }
    337 	|	FORCE_COMMON_ALLOCATION
    338 		{ command_line.force_common_definition = TRUE ; }
    339 	|	INHIBIT_COMMON_ALLOCATION
    340 		{ command_line.inhibit_common_definition = TRUE ; }
    341 	|	INPUT '(' input_list ')'
    342 	|	GROUP
    343 		  { lang_enter_group (); }
    344 		    '(' input_list ')'
    345 		  { lang_leave_group (); }
    346      	|	MAP '(' filename ')'
    347 		{ lang_add_map($3); }
    348 	|	INCLUDE filename
    349 		{ ldlex_script (); ldfile_open_command_file($2); }
    350 		ifile_list END
    351 		{ ldlex_popstate (); }
    352 	|	NOCROSSREFS '(' nocrossref_list ')'
    353 		{
    354 		  lang_add_nocrossref ($3);
    355 		}
    356 	|	NOCROSSREFS_TO '(' nocrossref_list ')'
    357 		{
    358 		  lang_add_nocrossref_to ($3);
    359 		}
    360 	|	EXTERN '(' extern_name_list ')'
    361 	|	INSERT_K AFTER NAME
    362 		{ lang_add_insert ($3, 0); }
    363 	|	INSERT_K BEFORE NAME
    364 		{ lang_add_insert ($3, 1); }
    365 	|	REGION_ALIAS '(' NAME ',' NAME ')'
    366 		{ lang_memory_region_alias ($3, $5); }
    367 	|	LD_FEATURE '(' NAME ')'
    368 		{ lang_ld_feature ($3); }
    369 	;
    370 
    371 input_list:
    372 		{ ldlex_inputlist(); }
    373 		input_list1
    374 		{ ldlex_popstate(); }
    375 
    376 input_list1:
    377 		NAME
    378 		{ lang_add_input_file($1,lang_input_file_is_search_file_enum,
    379 				 (char *)NULL); }
    380 	|	input_list1 ',' NAME
    381 		{ lang_add_input_file($3,lang_input_file_is_search_file_enum,
    382 				 (char *)NULL); }
    383 	|	input_list1 NAME
    384 		{ lang_add_input_file($2,lang_input_file_is_search_file_enum,
    385 				 (char *)NULL); }
    386 	|	LNAME
    387 		{ lang_add_input_file($1,lang_input_file_is_l_enum,
    388 				 (char *)NULL); }
    389 	|	input_list1 ',' LNAME
    390 		{ lang_add_input_file($3,lang_input_file_is_l_enum,
    391 				 (char *)NULL); }
    392 	|	input_list1 LNAME
    393 		{ lang_add_input_file($2,lang_input_file_is_l_enum,
    394 				 (char *)NULL); }
    395 	|	AS_NEEDED '('
    396 		  { $<integer>$ = input_flags.add_DT_NEEDED_for_regular;
    397 		    input_flags.add_DT_NEEDED_for_regular = TRUE; }
    398 		     input_list1 ')'
    399 		  { input_flags.add_DT_NEEDED_for_regular = $<integer>3; }
    400 	|	input_list1 ',' AS_NEEDED '('
    401 		  { $<integer>$ = input_flags.add_DT_NEEDED_for_regular;
    402 		    input_flags.add_DT_NEEDED_for_regular = TRUE; }
    403 		     input_list1 ')'
    404 		  { input_flags.add_DT_NEEDED_for_regular = $<integer>5; }
    405 	|	input_list1 AS_NEEDED '('
    406 		  { $<integer>$ = input_flags.add_DT_NEEDED_for_regular;
    407 		    input_flags.add_DT_NEEDED_for_regular = TRUE; }
    408 		     input_list1 ')'
    409 		  { input_flags.add_DT_NEEDED_for_regular = $<integer>4; }
    410 	;
    411 
    412 sections:
    413 		SECTIONS '{' sec_or_group_p1 '}'
    414 	;
    415 
    416 sec_or_group_p1:
    417 		sec_or_group_p1 section
    418 	|	sec_or_group_p1 statement_anywhere
    419 	|
    420 	;
    421 
    422 statement_anywhere:
    423 		ENTRY '(' NAME ')'
    424 		{ lang_add_entry ($3, FALSE); }
    425 	|	assignment end
    426 	|	ASSERT_K  {ldlex_expression ();} '(' exp ',' NAME ')'
    427 		{ ldlex_popstate ();
    428 		  lang_add_assignment (exp_assert ($4, $6)); }
    429 	;
    430 
    431 /* The '*' and '?' cases are there because the lexer returns them as
    432    separate tokens rather than as NAME.  */
    433 wildcard_name:
    434 		NAME
    435 			{
    436 			  $$ = $1;
    437 			}
    438 	|	'*'
    439 			{
    440 			  $$ = "*";
    441 			}
    442 	|	'?'
    443 			{
    444 			  $$ = "?";
    445 			}
    446 	;
    447 
    448 wildcard_spec:
    449 		wildcard_name
    450 			{
    451 			  $$.name = $1;
    452 			  $$.sorted = none;
    453 			  $$.exclude_name_list = NULL;
    454 			  $$.section_flag_list = NULL;
    455 			}
    456 	| 	EXCLUDE_FILE '(' exclude_name_list ')' wildcard_name
    457 			{
    458 			  $$.name = $5;
    459 			  $$.sorted = none;
    460 			  $$.exclude_name_list = $3;
    461 			  $$.section_flag_list = NULL;
    462 			}
    463 	|	SORT_BY_NAME '(' wildcard_name ')'
    464 			{
    465 			  $$.name = $3;
    466 			  $$.sorted = by_name;
    467 			  $$.exclude_name_list = NULL;
    468 			  $$.section_flag_list = NULL;
    469 			}
    470 	|	SORT_BY_ALIGNMENT '(' wildcard_name ')'
    471 			{
    472 			  $$.name = $3;
    473 			  $$.sorted = by_alignment;
    474 			  $$.exclude_name_list = NULL;
    475 			  $$.section_flag_list = NULL;
    476 			}
    477 	|	SORT_NONE '(' wildcard_name ')'
    478 			{
    479 			  $$.name = $3;
    480 			  $$.sorted = by_none;
    481 			  $$.exclude_name_list = NULL;
    482 			  $$.section_flag_list = NULL;
    483 			}
    484 	|	SORT_BY_NAME '(' SORT_BY_ALIGNMENT '(' wildcard_name ')' ')'
    485 			{
    486 			  $$.name = $5;
    487 			  $$.sorted = by_name_alignment;
    488 			  $$.exclude_name_list = NULL;
    489 			  $$.section_flag_list = NULL;
    490 			}
    491 	|	SORT_BY_NAME '(' SORT_BY_NAME '(' wildcard_name ')' ')'
    492 			{
    493 			  $$.name = $5;
    494 			  $$.sorted = by_name;
    495 			  $$.exclude_name_list = NULL;
    496 			  $$.section_flag_list = NULL;
    497 			}
    498 	|	SORT_BY_ALIGNMENT '(' SORT_BY_NAME '(' wildcard_name ')' ')'
    499 			{
    500 			  $$.name = $5;
    501 			  $$.sorted = by_alignment_name;
    502 			  $$.exclude_name_list = NULL;
    503 			  $$.section_flag_list = NULL;
    504 			}
    505 	|	SORT_BY_ALIGNMENT '(' SORT_BY_ALIGNMENT '(' wildcard_name ')' ')'
    506 			{
    507 			  $$.name = $5;
    508 			  $$.sorted = by_alignment;
    509 			  $$.exclude_name_list = NULL;
    510 			  $$.section_flag_list = NULL;
    511 			}
    512 	|	SORT_BY_NAME '(' EXCLUDE_FILE '(' exclude_name_list ')' wildcard_name ')'
    513 			{
    514 			  $$.name = $7;
    515 			  $$.sorted = by_name;
    516 			  $$.exclude_name_list = $5;
    517 			  $$.section_flag_list = NULL;
    518 			}
    519 	|	SORT_BY_INIT_PRIORITY '(' wildcard_name ')'
    520 			{
    521 			  $$.name = $3;
    522 			  $$.sorted = by_init_priority;
    523 			  $$.exclude_name_list = NULL;
    524 			  $$.section_flag_list = NULL;
    525 			}
    526 	;
    527 
    528 sect_flag_list:	NAME
    529 			{
    530 			  struct flag_info_list *n;
    531 			  n = ((struct flag_info_list *) xmalloc (sizeof *n));
    532 			  if ($1[0] == '!')
    533 			    {
    534 			      n->with = without_flags;
    535 			      n->name = &$1[1];
    536 			    }
    537 			  else
    538 			    {
    539 			      n->with = with_flags;
    540 			      n->name = $1;
    541 			    }
    542 			  n->valid = FALSE;
    543 			  n->next = NULL;
    544 			  $$ = n;
    545 			}
    546 	|	sect_flag_list '&' NAME
    547 			{
    548 			  struct flag_info_list *n;
    549 			  n = ((struct flag_info_list *) xmalloc (sizeof *n));
    550 			  if ($3[0] == '!')
    551 			    {
    552 			      n->with = without_flags;
    553 			      n->name = &$3[1];
    554 			    }
    555 			  else
    556 			    {
    557 			      n->with = with_flags;
    558 			      n->name = $3;
    559 			    }
    560 			  n->valid = FALSE;
    561 			  n->next = $1;
    562 			  $$ = n;
    563 			}
    564 	;
    565 
    566 sect_flags:
    567 		INPUT_SECTION_FLAGS '(' sect_flag_list ')'
    568 			{
    569 			  struct flag_info *n;
    570 			  n = ((struct flag_info *) xmalloc (sizeof *n));
    571 			  n->flag_list = $3;
    572 			  n->flags_initialized = FALSE;
    573 			  n->not_with_flags = 0;
    574 			  n->only_with_flags = 0;
    575 			  $$ = n;
    576 			}
    577 	;
    578 
    579 exclude_name_list:
    580 		exclude_name_list wildcard_name
    581 			{
    582 			  struct name_list *tmp;
    583 			  tmp = (struct name_list *) xmalloc (sizeof *tmp);
    584 			  tmp->name = $2;
    585 			  tmp->next = $1;
    586 			  $$ = tmp;
    587 			}
    588 	|
    589 		wildcard_name
    590 			{
    591 			  struct name_list *tmp;
    592 			  tmp = (struct name_list *) xmalloc (sizeof *tmp);
    593 			  tmp->name = $1;
    594 			  tmp->next = NULL;
    595 			  $$ = tmp;
    596 			}
    597 	;
    598 
    599 file_NAME_list:
    600 		file_NAME_list opt_comma wildcard_spec
    601 			{
    602 			  struct wildcard_list *tmp;
    603 			  tmp = (struct wildcard_list *) xmalloc (sizeof *tmp);
    604 			  tmp->next = $1;
    605 			  tmp->spec = $3;
    606 			  $$ = tmp;
    607 			}
    608 	|
    609 		wildcard_spec
    610 			{
    611 			  struct wildcard_list *tmp;
    612 			  tmp = (struct wildcard_list *) xmalloc (sizeof *tmp);
    613 			  tmp->next = NULL;
    614 			  tmp->spec = $1;
    615 			  $$ = tmp;
    616 			}
    617 	;
    618 
    619 input_section_spec_no_keep:
    620 		NAME
    621 			{
    622 			  struct wildcard_spec tmp;
    623 			  tmp.name = $1;
    624 			  tmp.exclude_name_list = NULL;
    625 			  tmp.sorted = none;
    626 			  tmp.section_flag_list = NULL;
    627 			  lang_add_wild (&tmp, NULL, ldgram_had_keep);
    628 			}
    629 	|	sect_flags NAME
    630 			{
    631 			  struct wildcard_spec tmp;
    632 			  tmp.name = $2;
    633 			  tmp.exclude_name_list = NULL;
    634 			  tmp.sorted = none;
    635 			  tmp.section_flag_list = $1;
    636 			  lang_add_wild (&tmp, NULL, ldgram_had_keep);
    637 			}
    638         |	'[' file_NAME_list ']'
    639 			{
    640 			  lang_add_wild (NULL, $2, ldgram_had_keep);
    641 			}
    642         |	sect_flags '[' file_NAME_list ']'
    643 			{
    644 			  struct wildcard_spec tmp;
    645 			  tmp.name = NULL;
    646 			  tmp.exclude_name_list = NULL;
    647 			  tmp.sorted = none;
    648 			  tmp.section_flag_list = $1;
    649 			  lang_add_wild (&tmp, $3, ldgram_had_keep);
    650 			}
    651 	|	wildcard_spec '(' file_NAME_list ')'
    652 			{
    653 			  lang_add_wild (&$1, $3, ldgram_had_keep);
    654 			}
    655 	|	sect_flags wildcard_spec '(' file_NAME_list ')'
    656 			{
    657 			  $2.section_flag_list = $1;
    658 			  lang_add_wild (&$2, $4, ldgram_had_keep);
    659 			}
    660 	;
    661 
    662 input_section_spec:
    663 		input_section_spec_no_keep
    664 	|	KEEP '('
    665 			{ ldgram_had_keep = TRUE; }
    666 		input_section_spec_no_keep ')'
    667 			{ ldgram_had_keep = FALSE; }
    668 	;
    669 
    670 statement:
    671 	  	assignment end
    672 	|	CREATE_OBJECT_SYMBOLS
    673 		{
    674  		lang_add_attribute(lang_object_symbols_statement_enum);
    675 	      	}
    676         |	';'
    677         |	CONSTRUCTORS
    678 		{
    679 
    680 		  lang_add_attribute(lang_constructors_statement_enum);
    681 		}
    682 	| SORT_BY_NAME '(' CONSTRUCTORS ')'
    683 		{
    684 		  constructors_sorted = TRUE;
    685 		  lang_add_attribute (lang_constructors_statement_enum);
    686 		}
    687 	| input_section_spec
    688         | length '(' mustbe_exp ')'
    689         	        {
    690 			  lang_add_data ((int) $1, $3);
    691 			}
    692 
    693 	| FILL '(' fill_exp ')'
    694 			{
    695 			  lang_add_fill ($3);
    696 			}
    697 	| ASSERT_K  {ldlex_expression ();} '(' exp ',' NAME ')' end
    698 			{ ldlex_popstate ();
    699 			  lang_add_assignment (exp_assert ($4, $6)); }
    700 	| INCLUDE filename
    701 		{ ldlex_script (); ldfile_open_command_file($2); }
    702 		statement_list_opt END
    703 		{ ldlex_popstate (); }
    704 	;
    705 
    706 statement_list:
    707 		statement_list statement
    708   	|  	statement
    709 	;
    710 
    711 statement_list_opt:
    712 		/* empty */
    713 	|	statement_list
    714 	;
    715 
    716 length:
    717 		QUAD
    718 			{ $$ = $1; }
    719 	|	SQUAD
    720 			{ $$ = $1; }
    721 	|	LONG
    722 			{ $$ = $1; }
    723 	| 	SHORT
    724 			{ $$ = $1; }
    725 	|	BYTE
    726 			{ $$ = $1; }
    727 	;
    728 
    729 fill_exp:
    730 	mustbe_exp
    731 		{
    732 		  $$ = exp_get_fill ($1, 0, "fill value");
    733 		}
    734 	;
    735 
    736 fill_opt:
    737 	  '=' fill_exp
    738 		{ $$ = $2; }
    739 	| 	{ $$ = (fill_type *) 0; }
    740 	;
    741 
    742 assign_op:
    743 		PLUSEQ
    744 			{ $$ = '+'; }
    745 	|	MINUSEQ
    746 			{ $$ = '-'; }
    747 	| 	MULTEQ
    748 			{ $$ = '*'; }
    749 	| 	DIVEQ
    750 			{ $$ = '/'; }
    751 	| 	LSHIFTEQ
    752 			{ $$ = LSHIFT; }
    753 	| 	RSHIFTEQ
    754 			{ $$ = RSHIFT; }
    755 	| 	ANDEQ
    756 			{ $$ = '&'; }
    757 	| 	OREQ
    758 			{ $$ = '|'; }
    759 
    760 	;
    761 
    762 end:	';' | ','
    763 	;
    764 
    765 
    766 assignment:
    767 		NAME '=' mustbe_exp
    768 		{
    769 		  lang_add_assignment (exp_assign ($1, $3, FALSE));
    770 		}
    771 	|	NAME assign_op mustbe_exp
    772 		{
    773 		  lang_add_assignment (exp_assign ($1,
    774 						   exp_binop ($2,
    775 							      exp_nameop (NAME,
    776 									  $1),
    777 							      $3), FALSE));
    778 		}
    779 	|	HIDDEN '(' NAME '=' mustbe_exp ')'
    780 		{
    781 		  lang_add_assignment (exp_assign ($3, $5, TRUE));
    782 		}
    783 	|	PROVIDE '(' NAME '=' mustbe_exp ')'
    784 		{
    785 		  lang_add_assignment (exp_provide ($3, $5, FALSE));
    786 		}
    787 	|	PROVIDE_HIDDEN '(' NAME '=' mustbe_exp ')'
    788 		{
    789 		  lang_add_assignment (exp_provide ($3, $5, TRUE));
    790 		}
    791 	;
    792 
    793 
    794 opt_comma:
    795 		','	|	;
    796 
    797 
    798 memory:
    799 		MEMORY '{' memory_spec_list_opt '}'
    800 	;
    801 
    802 memory_spec_list_opt: memory_spec_list | ;
    803 
    804 memory_spec_list:
    805 		memory_spec_list opt_comma memory_spec
    806 	|	memory_spec
    807 	;
    808 
    809 
    810 memory_spec: 	NAME
    811 		{ region = lang_memory_region_lookup ($1, TRUE); }
    812 		attributes_opt ':'
    813 		origin_spec opt_comma length_spec
    814 		{}
    815 	|	INCLUDE filename
    816 		{ ldlex_script (); ldfile_open_command_file($2); }
    817 		memory_spec_list_opt END
    818 		{ ldlex_popstate (); }
    819 	;
    820 
    821 origin_spec:
    822 	ORIGIN '=' mustbe_exp
    823 		{
    824 		  region->origin_exp = $3;
    825 		  region->current = region->origin;
    826 		}
    827 	;
    828 
    829 length_spec:
    830              LENGTH '=' mustbe_exp
    831 		{
    832 		  region->length_exp = $3;
    833 		}
    834 	;
    835 
    836 attributes_opt:
    837 		/* empty */
    838 		  { /* dummy action to avoid bison 1.25 error message */ }
    839 	|	'(' attributes_list ')'
    840 	;
    841 
    842 attributes_list:
    843 		attributes_string
    844 	|	attributes_list attributes_string
    845 	;
    846 
    847 attributes_string:
    848 		NAME
    849 		  { lang_set_flags (region, $1, 0); }
    850 	|	'!' NAME
    851 		  { lang_set_flags (region, $2, 1); }
    852 	;
    853 
    854 startup:
    855 	STARTUP '(' filename ')'
    856 		{ lang_startup($3); }
    857 	;
    858 
    859 high_level_library:
    860 		HLL '(' high_level_library_NAME_list ')'
    861 	|	HLL '(' ')'
    862 			{ ldemul_hll((char *)NULL); }
    863 	;
    864 
    865 high_level_library_NAME_list:
    866 		high_level_library_NAME_list opt_comma filename
    867 			{ ldemul_hll($3); }
    868 	|	filename
    869 			{ ldemul_hll($1); }
    870 
    871 	;
    872 
    873 low_level_library:
    874 	SYSLIB '(' low_level_library_NAME_list ')'
    875 	; low_level_library_NAME_list:
    876 		low_level_library_NAME_list opt_comma filename
    877 			{ ldemul_syslib($3); }
    878 	|
    879 	;
    880 
    881 floating_point_support:
    882 		FLOAT
    883 			{ lang_float(TRUE); }
    884 	|	NOFLOAT
    885 			{ lang_float(FALSE); }
    886 	;
    887 
    888 nocrossref_list:
    889 		/* empty */
    890 		{
    891 		  $$ = NULL;
    892 		}
    893 	|	NAME nocrossref_list
    894 		{
    895 		  struct lang_nocrossref *n;
    896 
    897 		  n = (struct lang_nocrossref *) xmalloc (sizeof *n);
    898 		  n->name = $1;
    899 		  n->next = $2;
    900 		  $$ = n;
    901 		}
    902 	|	NAME ',' nocrossref_list
    903 		{
    904 		  struct lang_nocrossref *n;
    905 
    906 		  n = (struct lang_nocrossref *) xmalloc (sizeof *n);
    907 		  n->name = $1;
    908 		  n->next = $3;
    909 		  $$ = n;
    910 		}
    911 	;
    912 
    913 mustbe_exp:		 { ldlex_expression (); }
    914 		exp
    915 			 { ldlex_popstate (); $$=$2;}
    916 	;
    917 
    918 exp	:
    919 		'-' exp %prec UNARY
    920 			{ $$ = exp_unop ('-', $2); }
    921 	|	'(' exp ')'
    922 			{ $$ = $2; }
    923 	|	NEXT '(' exp ')' %prec UNARY
    924 			{ $$ = exp_unop ((int) $1,$3); }
    925 	|	'!' exp %prec UNARY
    926 			{ $$ = exp_unop ('!', $2); }
    927 	|	'+' exp %prec UNARY
    928 			{ $$ = $2; }
    929 	|	'~' exp %prec UNARY
    930 			{ $$ = exp_unop ('~', $2);}
    931 
    932 	|	exp '*' exp
    933 			{ $$ = exp_binop ('*', $1, $3); }
    934 	|	exp '/' exp
    935 			{ $$ = exp_binop ('/', $1, $3); }
    936 	|	exp '%' exp
    937 			{ $$ = exp_binop ('%', $1, $3); }
    938 	|	exp '+' exp
    939 			{ $$ = exp_binop ('+', $1, $3); }
    940 	|	exp '-' exp
    941 			{ $$ = exp_binop ('-' , $1, $3); }
    942 	|	exp LSHIFT exp
    943 			{ $$ = exp_binop (LSHIFT , $1, $3); }
    944 	|	exp RSHIFT exp
    945 			{ $$ = exp_binop (RSHIFT , $1, $3); }
    946 	|	exp EQ exp
    947 			{ $$ = exp_binop (EQ , $1, $3); }
    948 	|	exp NE exp
    949 			{ $$ = exp_binop (NE , $1, $3); }
    950 	|	exp LE exp
    951 			{ $$ = exp_binop (LE , $1, $3); }
    952   	|	exp GE exp
    953 			{ $$ = exp_binop (GE , $1, $3); }
    954 	|	exp '<' exp
    955 			{ $$ = exp_binop ('<' , $1, $3); }
    956 	|	exp '>' exp
    957 			{ $$ = exp_binop ('>' , $1, $3); }
    958 	|	exp '&' exp
    959 			{ $$ = exp_binop ('&' , $1, $3); }
    960 	|	exp '^' exp
    961 			{ $$ = exp_binop ('^' , $1, $3); }
    962 	|	exp '|' exp
    963 			{ $$ = exp_binop ('|' , $1, $3); }
    964 	|	exp '?' exp ':' exp
    965 			{ $$ = exp_trinop ('?' , $1, $3, $5); }
    966 	|	exp ANDAND exp
    967 			{ $$ = exp_binop (ANDAND , $1, $3); }
    968 	|	exp OROR exp
    969 			{ $$ = exp_binop (OROR , $1, $3); }
    970 	|	DEFINED '(' NAME ')'
    971 			{ $$ = exp_nameop (DEFINED, $3); }
    972 	|	INT
    973 			{ $$ = exp_bigintop ($1.integer, $1.str); }
    974         |	SIZEOF_HEADERS
    975 			{ $$ = exp_nameop (SIZEOF_HEADERS,0); }
    976 
    977 	|	ALIGNOF '(' NAME ')'
    978 			{ $$ = exp_nameop (ALIGNOF,$3); }
    979 	|	SIZEOF '(' NAME ')'
    980 			{ $$ = exp_nameop (SIZEOF,$3); }
    981 	|	ADDR '(' NAME ')'
    982 			{ $$ = exp_nameop (ADDR,$3); }
    983 	|	LOADADDR '(' NAME ')'
    984 			{ $$ = exp_nameop (LOADADDR,$3); }
    985 	|	CONSTANT '(' NAME ')'
    986 			{ $$ = exp_nameop (CONSTANT,$3); }
    987 	|	ABSOLUTE '(' exp ')'
    988 			{ $$ = exp_unop (ABSOLUTE, $3); }
    989 	|	ALIGN_K '(' exp ')'
    990 			{ $$ = exp_unop (ALIGN_K,$3); }
    991 	|	ALIGN_K '(' exp ',' exp ')'
    992 			{ $$ = exp_binop (ALIGN_K,$3,$5); }
    993 	|	DATA_SEGMENT_ALIGN '(' exp ',' exp ')'
    994 			{ $$ = exp_binop (DATA_SEGMENT_ALIGN, $3, $5); }
    995 	|	DATA_SEGMENT_RELRO_END '(' exp ',' exp ')'
    996 			{ $$ = exp_binop (DATA_SEGMENT_RELRO_END, $5, $3); }
    997 	|	DATA_SEGMENT_END '(' exp ')'
    998 			{ $$ = exp_unop (DATA_SEGMENT_END, $3); }
    999         |       SEGMENT_START '(' NAME ',' exp ')'
   1000                         { /* The operands to the expression node are
   1001 			     placed in the opposite order from the way
   1002 			     in which they appear in the script as
   1003 			     that allows us to reuse more code in
   1004 			     fold_binary.  */
   1005 			  $$ = exp_binop (SEGMENT_START,
   1006 					  $5,
   1007 					  exp_nameop (NAME, $3)); }
   1008 	|	BLOCK '(' exp ')'
   1009 			{ $$ = exp_unop (ALIGN_K,$3); }
   1010 	|	NAME
   1011 			{ $$ = exp_nameop (NAME,$1); }
   1012 	|	MAX_K '(' exp ',' exp ')'
   1013 			{ $$ = exp_binop (MAX_K, $3, $5 ); }
   1014 	|	MIN_K '(' exp ',' exp ')'
   1015 			{ $$ = exp_binop (MIN_K, $3, $5 ); }
   1016 	|	ASSERT_K '(' exp ',' NAME ')'
   1017 			{ $$ = exp_assert ($3, $5); }
   1018 	|	ORIGIN '(' NAME ')'
   1019 			{ $$ = exp_nameop (ORIGIN, $3); }
   1020 	|	LENGTH '(' NAME ')'
   1021 			{ $$ = exp_nameop (LENGTH, $3); }
   1022 	|	LOG2CEIL '(' exp ')'
   1023 			{ $$ = exp_unop (LOG2CEIL, $3); }
   1024 	;
   1025 
   1026 
   1027 memspec_at_opt:
   1028                 AT '>' NAME { $$ = $3; }
   1029         |       { $$ = 0; }
   1030         ;
   1031 
   1032 opt_at:
   1033 		AT '(' exp ')' { $$ = $3; }
   1034 	|	{ $$ = 0; }
   1035 	;
   1036 
   1037 opt_align:
   1038 		ALIGN_K '(' exp ')' { $$ = $3; }
   1039 	|	{ $$ = 0; }
   1040 	;
   1041 
   1042 opt_align_with_input:
   1043 		ALIGN_WITH_INPUT { $$ = ALIGN_WITH_INPUT; }
   1044 	|	{ $$ = 0; }
   1045 	;
   1046 
   1047 opt_subalign:
   1048 		SUBALIGN '(' exp ')' { $$ = $3; }
   1049 	|	{ $$ = 0; }
   1050 	;
   1051 
   1052 sect_constraint:
   1053 		ONLY_IF_RO { $$ = ONLY_IF_RO; }
   1054 	|	ONLY_IF_RW { $$ = ONLY_IF_RW; }
   1055 	|	SPECIAL { $$ = SPECIAL; }
   1056 	|	{ $$ = 0; }
   1057 	;
   1058 
   1059 section:	NAME 		{ ldlex_expression(); }
   1060 		opt_exp_with_type
   1061 		opt_at
   1062 		opt_align
   1063 		opt_align_with_input
   1064 		opt_subalign	{ ldlex_popstate (); ldlex_script (); }
   1065 		sect_constraint
   1066 		'{'
   1067 			{
   1068 			  lang_enter_output_section_statement($1, $3,
   1069 							      sectype,
   1070 							      $5, $7, $4, $9, $6);
   1071 			}
   1072 		statement_list_opt
   1073  		'}' { ldlex_popstate (); ldlex_expression (); }
   1074 		memspec_opt memspec_at_opt phdr_opt fill_opt
   1075 		{
   1076 		  ldlex_popstate ();
   1077 		  lang_leave_output_section_statement ($18, $15, $17, $16);
   1078 		}
   1079 		opt_comma
   1080 		{}
   1081 	|	OVERLAY
   1082 			{ ldlex_expression (); }
   1083 		opt_exp_without_type opt_nocrossrefs opt_at opt_subalign
   1084 			{ ldlex_popstate (); ldlex_script (); }
   1085 		'{'
   1086 			{
   1087 			  lang_enter_overlay ($3, $6);
   1088 			}
   1089 		overlay_section
   1090 		'}'
   1091 			{ ldlex_popstate (); ldlex_expression (); }
   1092 		memspec_opt memspec_at_opt phdr_opt fill_opt
   1093 			{
   1094 			  ldlex_popstate ();
   1095 			  lang_leave_overlay ($5, (int) $4,
   1096 					      $16, $13, $15, $14);
   1097 			}
   1098 		opt_comma
   1099 	|	/* The GROUP case is just enough to support the gcc
   1100 		   svr3.ifile script.  It is not intended to be full
   1101 		   support.  I'm not even sure what GROUP is supposed
   1102 		   to mean.  */
   1103 		GROUP { ldlex_expression (); }
   1104 		opt_exp_with_type
   1105 		{
   1106 		  ldlex_popstate ();
   1107 		  lang_add_assignment (exp_assign (".", $3, FALSE));
   1108 		}
   1109 		'{' sec_or_group_p1 '}'
   1110 	|	INCLUDE filename
   1111 		{ ldlex_script (); ldfile_open_command_file($2); }
   1112 		sec_or_group_p1 END
   1113 		{ ldlex_popstate (); }
   1114 	;
   1115 
   1116 type:
   1117 	   NOLOAD  { sectype = noload_section; }
   1118 	|  DSECT   { sectype = noalloc_section; }
   1119 	|  COPY    { sectype = noalloc_section; }
   1120 	|  INFO    { sectype = noalloc_section; }
   1121 	|  OVERLAY { sectype = noalloc_section; }
   1122 	;
   1123 
   1124 atype:
   1125 	 	'(' type ')'
   1126   	| 	/* EMPTY */ { sectype = normal_section; }
   1127   	| 	'(' ')' { sectype = normal_section; }
   1128 	;
   1129 
   1130 opt_exp_with_type:
   1131 		exp atype ':'		{ $$ = $1; }
   1132 	|	atype ':'		{ $$ = (etree_type *)NULL;  }
   1133 	|	/* The BIND cases are to support the gcc svr3.ifile
   1134 		   script.  They aren't intended to implement full
   1135 		   support for the BIND keyword.  I'm not even sure
   1136 		   what BIND is supposed to mean.  */
   1137 		BIND '(' exp ')' atype ':' { $$ = $3; }
   1138 	|	BIND '(' exp ')' BLOCK '(' exp ')' atype ':'
   1139 		{ $$ = $3; }
   1140 	;
   1141 
   1142 opt_exp_without_type:
   1143 		exp ':'		{ $$ = $1; }
   1144 	|	':'		{ $$ = (etree_type *) NULL;  }
   1145 	;
   1146 
   1147 opt_nocrossrefs:
   1148 		/* empty */
   1149 			{ $$ = 0; }
   1150 	|	NOCROSSREFS
   1151 			{ $$ = 1; }
   1152 	;
   1153 
   1154 memspec_opt:
   1155 		'>' NAME
   1156 		{ $$ = $2; }
   1157 	|	{ $$ = DEFAULT_MEMORY_REGION; }
   1158 	;
   1159 
   1160 phdr_opt:
   1161 		/* empty */
   1162 		{
   1163 		  $$ = NULL;
   1164 		}
   1165 	|	phdr_opt ':' NAME
   1166 		{
   1167 		  struct lang_output_section_phdr_list *n;
   1168 
   1169 		  n = ((struct lang_output_section_phdr_list *)
   1170 		       xmalloc (sizeof *n));
   1171 		  n->name = $3;
   1172 		  n->used = FALSE;
   1173 		  n->next = $1;
   1174 		  $$ = n;
   1175 		}
   1176 	;
   1177 
   1178 overlay_section:
   1179 		/* empty */
   1180 	|	overlay_section
   1181 		NAME
   1182 			{
   1183 			  ldlex_script ();
   1184 			  lang_enter_overlay_section ($2);
   1185 			}
   1186 		'{' statement_list_opt '}'
   1187 			{ ldlex_popstate (); ldlex_expression (); }
   1188 		phdr_opt fill_opt
   1189 			{
   1190 			  ldlex_popstate ();
   1191 			  lang_leave_overlay_section ($9, $8);
   1192 			}
   1193 		opt_comma
   1194 	;
   1195 
   1196 phdrs:
   1197 		PHDRS '{' phdr_list '}'
   1198 	;
   1199 
   1200 phdr_list:
   1201 		/* empty */
   1202 	|	phdr_list phdr
   1203 	;
   1204 
   1205 phdr:
   1206 		NAME { ldlex_expression (); }
   1207 		  phdr_type phdr_qualifiers { ldlex_popstate (); }
   1208 		  ';'
   1209 		{
   1210 		  lang_new_phdr ($1, $3, $4.filehdr, $4.phdrs, $4.at,
   1211 				 $4.flags);
   1212 		}
   1213 	;
   1214 
   1215 phdr_type:
   1216 		exp
   1217 		{
   1218 		  $$ = $1;
   1219 
   1220 		  if ($1->type.node_class == etree_name
   1221 		      && $1->type.node_code == NAME)
   1222 		    {
   1223 		      const char *s;
   1224 		      unsigned int i;
   1225 		      static const char * const phdr_types[] =
   1226 			{
   1227 			  "PT_NULL", "PT_LOAD", "PT_DYNAMIC",
   1228 			  "PT_INTERP", "PT_NOTE", "PT_SHLIB",
   1229 			  "PT_PHDR", "PT_TLS"
   1230 			};
   1231 
   1232 		      s = $1->name.name;
   1233 		      for (i = 0;
   1234 			   i < sizeof phdr_types / sizeof phdr_types[0];
   1235 			   i++)
   1236 			if (strcmp (s, phdr_types[i]) == 0)
   1237 			  {
   1238 			    $$ = exp_intop (i);
   1239 			    break;
   1240 			  }
   1241 		      if (i == sizeof phdr_types / sizeof phdr_types[0])
   1242 			{
   1243 			  if (strcmp (s, "PT_GNU_EH_FRAME") == 0)
   1244 			    $$ = exp_intop (0x6474e550);
   1245 			  else if (strcmp (s, "PT_GNU_STACK") == 0)
   1246 			    $$ = exp_intop (0x6474e551);
   1247 			  else
   1248 			    {
   1249 			      einfo (_("\
   1250 %X%P:%S: unknown phdr type `%s' (try integer literal)\n"),
   1251 				     NULL, s);
   1252 			      $$ = exp_intop (0);
   1253 			    }
   1254 			}
   1255 		    }
   1256 		}
   1257 	;
   1258 
   1259 phdr_qualifiers:
   1260 		/* empty */
   1261 		{
   1262 		  memset (&$$, 0, sizeof (struct phdr_info));
   1263 		}
   1264 	|	NAME phdr_val phdr_qualifiers
   1265 		{
   1266 		  $$ = $3;
   1267 		  if (strcmp ($1, "FILEHDR") == 0 && $2 == NULL)
   1268 		    $$.filehdr = TRUE;
   1269 		  else if (strcmp ($1, "PHDRS") == 0 && $2 == NULL)
   1270 		    $$.phdrs = TRUE;
   1271 		  else if (strcmp ($1, "FLAGS") == 0 && $2 != NULL)
   1272 		    $$.flags = $2;
   1273 		  else
   1274 		    einfo (_("%X%P:%S: PHDRS syntax error at `%s'\n"),
   1275 			   NULL, $1);
   1276 		}
   1277 	|	AT '(' exp ')' phdr_qualifiers
   1278 		{
   1279 		  $$ = $5;
   1280 		  $$.at = $3;
   1281 		}
   1282 	;
   1283 
   1284 phdr_val:
   1285 		/* empty */
   1286 		{
   1287 		  $$ = NULL;
   1288 		}
   1289 	| '(' exp ')'
   1290 		{
   1291 		  $$ = $2;
   1292 		}
   1293 	;
   1294 
   1295 dynamic_list_file:
   1296 		{
   1297 		  ldlex_version_file ();
   1298 		  PUSH_ERROR (_("dynamic list"));
   1299 		}
   1300 		dynamic_list_nodes
   1301 		{
   1302 		  ldlex_popstate ();
   1303 		  POP_ERROR ();
   1304 		}
   1305 	;
   1306 
   1307 dynamic_list_nodes:
   1308 		dynamic_list_node
   1309 	|	dynamic_list_nodes dynamic_list_node
   1310 	;
   1311 
   1312 dynamic_list_node:
   1313 		'{' dynamic_list_tag '}' ';'
   1314 	;
   1315 
   1316 dynamic_list_tag:
   1317 		vers_defns ';'
   1318 		{
   1319 		  lang_append_dynamic_list ($1);
   1320 		}
   1321 	;
   1322 
   1323 /* This syntax is used within an external version script file.  */
   1324 
   1325 version_script_file:
   1326 		{
   1327 		  ldlex_version_file ();
   1328 		  PUSH_ERROR (_("VERSION script"));
   1329 		}
   1330 		vers_nodes
   1331 		{
   1332 		  ldlex_popstate ();
   1333 		  POP_ERROR ();
   1334 		}
   1335 	;
   1336 
   1337 /* This is used within a normal linker script file.  */
   1338 
   1339 version:
   1340 		{
   1341 		  ldlex_version_script ();
   1342 		}
   1343 		VERSIONK '{' vers_nodes '}'
   1344 		{
   1345 		  ldlex_popstate ();
   1346 		}
   1347 	;
   1348 
   1349 vers_nodes:
   1350 		vers_node
   1351 	|	vers_nodes vers_node
   1352 	;
   1353 
   1354 vers_node:
   1355 		'{' vers_tag '}' ';'
   1356 		{
   1357 		  lang_register_vers_node (NULL, $2, NULL);
   1358 		}
   1359 	|	VERS_TAG '{' vers_tag '}' ';'
   1360 		{
   1361 		  lang_register_vers_node ($1, $3, NULL);
   1362 		}
   1363 	|	VERS_TAG '{' vers_tag '}' verdep ';'
   1364 		{
   1365 		  lang_register_vers_node ($1, $3, $5);
   1366 		}
   1367 	;
   1368 
   1369 verdep:
   1370 		VERS_TAG
   1371 		{
   1372 		  $$ = lang_add_vers_depend (NULL, $1);
   1373 		}
   1374 	|	verdep VERS_TAG
   1375 		{
   1376 		  $$ = lang_add_vers_depend ($1, $2);
   1377 		}
   1378 	;
   1379 
   1380 vers_tag:
   1381 		/* empty */
   1382 		{
   1383 		  $$ = lang_new_vers_node (NULL, NULL);
   1384 		}
   1385 	|	vers_defns ';'
   1386 		{
   1387 		  $$ = lang_new_vers_node ($1, NULL);
   1388 		}
   1389 	|	GLOBAL ':' vers_defns ';'
   1390 		{
   1391 		  $$ = lang_new_vers_node ($3, NULL);
   1392 		}
   1393 	|	LOCAL ':' vers_defns ';'
   1394 		{
   1395 		  $$ = lang_new_vers_node (NULL, $3);
   1396 		}
   1397 	|	GLOBAL ':' vers_defns ';' LOCAL ':' vers_defns ';'
   1398 		{
   1399 		  $$ = lang_new_vers_node ($3, $7);
   1400 		}
   1401 	;
   1402 
   1403 vers_defns:
   1404 		VERS_IDENTIFIER
   1405 		{
   1406 		  $$ = lang_new_vers_pattern (NULL, $1, ldgram_vers_current_lang, FALSE);
   1407 		}
   1408         |       NAME
   1409 		{
   1410 		  $$ = lang_new_vers_pattern (NULL, $1, ldgram_vers_current_lang, TRUE);
   1411 		}
   1412 	|	vers_defns ';' VERS_IDENTIFIER
   1413 		{
   1414 		  $$ = lang_new_vers_pattern ($1, $3, ldgram_vers_current_lang, FALSE);
   1415 		}
   1416 	|	vers_defns ';' NAME
   1417 		{
   1418 		  $$ = lang_new_vers_pattern ($1, $3, ldgram_vers_current_lang, TRUE);
   1419 		}
   1420 	|	vers_defns ';' EXTERN NAME '{'
   1421 			{
   1422 			  $<name>$ = ldgram_vers_current_lang;
   1423 			  ldgram_vers_current_lang = $4;
   1424 			}
   1425 		vers_defns opt_semicolon '}'
   1426 			{
   1427 			  struct bfd_elf_version_expr *pat;
   1428 			  for (pat = $7; pat->next != NULL; pat = pat->next);
   1429 			  pat->next = $1;
   1430 			  $$ = $7;
   1431 			  ldgram_vers_current_lang = $<name>6;
   1432 			}
   1433 	|	EXTERN NAME '{'
   1434 			{
   1435 			  $<name>$ = ldgram_vers_current_lang;
   1436 			  ldgram_vers_current_lang = $2;
   1437 			}
   1438 		vers_defns opt_semicolon '}'
   1439 			{
   1440 			  $$ = $5;
   1441 			  ldgram_vers_current_lang = $<name>4;
   1442 			}
   1443 	|	GLOBAL
   1444 		{
   1445 		  $$ = lang_new_vers_pattern (NULL, "global", ldgram_vers_current_lang, FALSE);
   1446 		}
   1447 	|	vers_defns ';' GLOBAL
   1448 		{
   1449 		  $$ = lang_new_vers_pattern ($1, "global", ldgram_vers_current_lang, FALSE);
   1450 		}
   1451 	|	LOCAL
   1452 		{
   1453 		  $$ = lang_new_vers_pattern (NULL, "local", ldgram_vers_current_lang, FALSE);
   1454 		}
   1455 	|	vers_defns ';' LOCAL
   1456 		{
   1457 		  $$ = lang_new_vers_pattern ($1, "local", ldgram_vers_current_lang, FALSE);
   1458 		}
   1459 	|	EXTERN
   1460 		{
   1461 		  $$ = lang_new_vers_pattern (NULL, "extern", ldgram_vers_current_lang, FALSE);
   1462 		}
   1463 	|	vers_defns ';' EXTERN
   1464 		{
   1465 		  $$ = lang_new_vers_pattern ($1, "extern", ldgram_vers_current_lang, FALSE);
   1466 		}
   1467 	;
   1468 
   1469 opt_semicolon:
   1470 		/* empty */
   1471 	|	';'
   1472 	;
   1473 
   1474 %%
   1475 void
   1476 yyerror(arg)
   1477      const char *arg;
   1478 {
   1479   if (ldfile_assumed_script)
   1480     einfo (_("%P:%s: file format not recognized; treating as linker script\n"),
   1481 	   ldlex_filename ());
   1482   if (error_index > 0 && error_index < ERROR_NAME_MAX)
   1483     einfo ("%P%F:%S: %s in %s\n", NULL, arg, error_names[error_index - 1]);
   1484   else
   1485     einfo ("%P%F:%S: %s\n", NULL, arg);
   1486 }
   1487