PR ld/12356
* ld.texinfo (Miscellaneous Commands): Describe LD_FEATURE. (Expression Section): Update. * ld.h (ld_config_type): Add sane_expr. * ldgram.y (ifile_p1): Add LD_FEATURE. * ldlex.l (LD_FEATYRE): New. * ldemul.c (after_parse_default): Delete code handling ld_compatibility. * ldexp.h (struct ldexp_control): Delete uses_defined. * ldexp.c: Remove all uses of uses_defined. (fold_name): Test config.sane_expr rather than ld_compatibility. (exp_fold_tree_1): Likewise. Adjust handling of assignments during first phase. * ldlang.h (ld_compatibility): Delete. (lang_ld_feature): Declare. * ldlang.c (ld_compatibility): Delete. (open_input_bfds): Only handle assignments for --defsym. (lang_ld_feature): New function.
This commit is contained in:
parent
2e57b2afce
commit
01554a74b5
10 changed files with 77 additions and 26 deletions
18
ld/ChangeLog
18
ld/ChangeLog
|
@ -1,5 +1,23 @@
|
|||
2011-01-13 Alan Modra <amodra@gmail.com>
|
||||
|
||||
PR ld/12356
|
||||
* ld.texinfo (Miscellaneous Commands): Describe LD_FEATURE.
|
||||
(Expression Section): Update.
|
||||
* ld.h (ld_config_type): Add sane_expr.
|
||||
* ldgram.y (ifile_p1): Add LD_FEATURE.
|
||||
* ldlex.l (LD_FEATYRE): New.
|
||||
* ldemul.c (after_parse_default): Delete code handling ld_compatibility.
|
||||
* ldexp.h (struct ldexp_control): Delete uses_defined.
|
||||
* ldexp.c: Remove all uses of uses_defined.
|
||||
(fold_name): Test config.sane_expr rather than ld_compatibility.
|
||||
(exp_fold_tree_1): Likewise. Adjust handling of assignments
|
||||
during first phase.
|
||||
* ldlang.h (ld_compatibility): Delete.
|
||||
(lang_ld_feature): Declare.
|
||||
* ldlang.c (ld_compatibility): Delete.
|
||||
(open_input_bfds): Only handle assignments for --defsym.
|
||||
(lang_ld_feature): New function.
|
||||
|
||||
PR ld/12356
|
||||
* ldexp.h (exp_assop): Delete.
|
||||
(exp_assign, exp_defsym): Declare.
|
||||
|
|
4
ld/ld.h
4
ld/ld.h
|
@ -292,6 +292,10 @@ typedef struct {
|
|||
on the command line. */
|
||||
bfd_boolean only_cmd_line_lib_dirs;
|
||||
|
||||
/* If set, numbers and absolute symbols are simply treated as
|
||||
numbers everywhere. */
|
||||
bfd_boolean sane_expr;
|
||||
|
||||
/* The rpath separation character. Usually ':'. */
|
||||
char rpath_separator;
|
||||
|
||||
|
|
|
@ -3344,6 +3344,13 @@ of the names used by the BFD library (@pxref{BFD}). You can see the
|
|||
architecture of an object file by using the @code{objdump} program with
|
||||
the @samp{-f} option.
|
||||
@end ifclear
|
||||
|
||||
@item LD_FEATURE(@var{string})
|
||||
@kindex LD_FEATURE(@var{string})
|
||||
This command may be used to modify @command{ld} behavior. If
|
||||
@var{string} is @code{"SANE_EXPR"} then absolute symbols and numbers
|
||||
in a script are simply treated as numbers everywhere.
|
||||
@xref{Expression Section}.
|
||||
@end table
|
||||
|
||||
@node Assignments
|
||||
|
@ -5503,15 +5510,15 @@ section relative symbols and for builtin functions that return an
|
|||
address, such as @code{ADDR}, @code{LOADADDR}, @code{ORIGIN} and
|
||||
@code{SEGMENT_START}. Other terms are simply numbers, or are builtin
|
||||
functions that return a non-address value, such as @code{LENGTH}.
|
||||
One complication is that unless you assign @code{__ld_compatibility}
|
||||
a value of 221 or larger, numbers and absolute symbols are treated
|
||||
One complication is that unless you set @code{LD_FEATURE ("SANE_EXPR")}
|
||||
(@pxref{Miscellaneous Commands}), numbers and absolute symbols are treated
|
||||
differently depending on their location, for compatibility with older
|
||||
versions of @code{ld}. Expressions appearing outside an output
|
||||
section definition treat all numbers as absolute addresses.
|
||||
Expressions appearing inside an output section definition treat
|
||||
absolute symbols as numbers. If @code{__ld_compatibility} is assigned
|
||||
a value larger than 221, then absolute symbols and numbers are simply
|
||||
treated as numbers everywhere.
|
||||
absolute symbols as numbers. If @code{LD_FEATURE ("SANE_EXPR")} is
|
||||
given, then absolute symbols and numbers are simply treated as numbers
|
||||
everywhere.
|
||||
|
||||
In the following simple example,
|
||||
|
||||
|
|
10
ld/ldemul.c
10
ld/ldemul.c
|
@ -226,16 +226,6 @@ after_parse_default (void)
|
|||
void
|
||||
after_open_default (void)
|
||||
{
|
||||
struct bfd_link_hash_entry *h;
|
||||
|
||||
h = bfd_wrapped_link_hash_lookup (link_info.output_bfd,
|
||||
&link_info,
|
||||
"__ld_compatibility",
|
||||
FALSE, FALSE, TRUE);
|
||||
if (h != NULL
|
||||
&& (h->type == bfd_link_hash_defined
|
||||
|| h->type == bfd_link_hash_defweak))
|
||||
ld_compatibility = h->u.def.value;
|
||||
}
|
||||
|
||||
void
|
||||
|
|
10
ld/ldexp.c
10
ld/ldexp.c
|
@ -512,7 +512,6 @@ fold_name (etree_type *tree)
|
|||
break;
|
||||
|
||||
case DEFINED:
|
||||
expld.uses_defined = TRUE;
|
||||
if (expld.phase == lang_first_phase_enum)
|
||||
lang_track_definedness (tree->name.name);
|
||||
else
|
||||
|
@ -564,7 +563,7 @@ fold_name (etree_type *tree)
|
|||
}
|
||||
else if (output_section == bfd_abs_section_ptr
|
||||
&& (expld.section != bfd_abs_section_ptr
|
||||
|| ld_compatibility >= 221))
|
||||
|| config.sane_expr))
|
||||
new_number (h->u.def.value + h->u.def.section->output_offset);
|
||||
else
|
||||
new_rel (h->u.def.value + h->u.def.section->output_offset,
|
||||
|
@ -712,7 +711,7 @@ exp_fold_tree_1 (etree_type *tree)
|
|||
{
|
||||
case etree_value:
|
||||
if (expld.section == bfd_abs_section_ptr
|
||||
&& ld_compatibility < 221)
|
||||
&& !config.sane_expr)
|
||||
new_abs (tree->value.value);
|
||||
else
|
||||
new_number (tree->value.value);
|
||||
|
@ -819,7 +818,8 @@ exp_fold_tree_1 (etree_type *tree)
|
|||
exp_fold_tree_1 (tree->assign.src);
|
||||
if (expld.result.valid_p
|
||||
|| (expld.phase == lang_first_phase_enum
|
||||
&& !expld.uses_defined))
|
||||
&& tree->type.node_class == etree_assign
|
||||
&& tree->assign.hidden))
|
||||
{
|
||||
if (h == NULL)
|
||||
{
|
||||
|
@ -883,7 +883,6 @@ exp_fold_tree (etree_type *tree, asection *current_section, bfd_vma *dotp)
|
|||
expld.dot = *dotp;
|
||||
expld.dotp = dotp;
|
||||
expld.section = current_section;
|
||||
expld.uses_defined = FALSE;
|
||||
exp_fold_tree_1 (tree);
|
||||
}
|
||||
|
||||
|
@ -893,7 +892,6 @@ exp_fold_tree_no_dot (etree_type *tree)
|
|||
expld.dot = 0;
|
||||
expld.dotp = NULL;
|
||||
expld.section = bfd_abs_section_ptr;
|
||||
expld.uses_defined = FALSE;
|
||||
exp_fold_tree_1 (tree);
|
||||
}
|
||||
|
||||
|
|
|
@ -132,8 +132,6 @@ struct ldexp_control {
|
|||
/* Working results. */
|
||||
etree_value_type result;
|
||||
bfd_vma dot;
|
||||
/* Set if an expression contains DEFINED(). */
|
||||
bfd_boolean uses_defined;
|
||||
|
||||
/* Current dot and section passed to ldexp folder. */
|
||||
bfd_vma *dotp;
|
||||
|
|
|
@ -134,6 +134,7 @@ static int error_index;
|
|||
%token INCLUDE
|
||||
%token MEMORY
|
||||
%token REGION_ALIAS
|
||||
%token LD_FEATURE
|
||||
%token NOLOAD DSECT COPY INFO OVERLAY
|
||||
%token DEFINED TARGET_K SEARCH_DIR MAP ENTRY
|
||||
%token <integer> NEXT
|
||||
|
@ -357,6 +358,8 @@ ifile_p1:
|
|||
{ lang_add_insert ($3, 1); }
|
||||
| REGION_ALIAS '(' NAME ',' NAME ')'
|
||||
{ lang_memory_region_alias ($3, $5); }
|
||||
| LD_FEATURE '(' NAME ')'
|
||||
{ lang_ld_feature ($3); }
|
||||
;
|
||||
|
||||
input_list:
|
||||
|
|
34
ld/ldlang.c
34
ld/ldlang.c
|
@ -108,7 +108,6 @@ bfd_boolean delete_output_file_on_failure = FALSE;
|
|||
struct lang_phdr *lang_phdr_list;
|
||||
struct lang_nocrossrefs *nocrossref_list;
|
||||
bfd_boolean missing_file = FALSE;
|
||||
int ld_compatibility;
|
||||
|
||||
/* Functions that traverse the linker script and might evaluate
|
||||
DEFINED() need to increment this. */
|
||||
|
@ -3250,7 +3249,9 @@ open_input_bfds (lang_statement_union_type *s, bfd_boolean force)
|
|||
}
|
||||
break;
|
||||
case lang_assignment_statement_enum:
|
||||
exp_fold_tree_no_dot (s->assignment_statement.exp);
|
||||
if (s->assignment_statement.exp->assign.hidden)
|
||||
/* This is from a --defsym on the command line. */
|
||||
exp_fold_tree_no_dot (s->assignment_statement.exp);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
|
@ -7845,3 +7846,32 @@ lang_append_dynamic_list_cpp_new (void)
|
|||
|
||||
lang_append_dynamic_list (dynamic);
|
||||
}
|
||||
|
||||
/* Scan a space and/or comma separated string of features. */
|
||||
|
||||
void
|
||||
lang_ld_feature (char *str)
|
||||
{
|
||||
char *p, *q;
|
||||
|
||||
p = str;
|
||||
while (*p)
|
||||
{
|
||||
char sep;
|
||||
while (*p == ',' || ISSPACE (*p))
|
||||
++p;
|
||||
if (!*p)
|
||||
break;
|
||||
q = p + 1;
|
||||
while (*q && *q != ',' && !ISSPACE (*q))
|
||||
++q;
|
||||
sep = *q;
|
||||
*q = 0;
|
||||
if (strcasecmp (p, "SANE_EXPR") == 0)
|
||||
config.sane_expr = TRUE;
|
||||
else
|
||||
einfo (_("%X%P: unknown feature `%s'\n"), p);
|
||||
*q = sep;
|
||||
p = q;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -469,7 +469,6 @@ extern bfd_boolean entry_from_cmdline;
|
|||
extern lang_statement_list_type file_chain;
|
||||
extern lang_statement_list_type input_file_chain;
|
||||
|
||||
extern int ld_compatibility;
|
||||
extern int lang_statement_iteration;
|
||||
extern bfd_boolean missing_file;
|
||||
|
||||
|
@ -651,4 +650,7 @@ extern bfd_boolean
|
|||
ldlang_override_segment_assignment
|
||||
(struct bfd_link_info *, bfd *, asection *, asection *, bfd_boolean);
|
||||
|
||||
extern void
|
||||
lang_ld_feature (char *);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -241,6 +241,7 @@ V_IDENTIFIER [*?.$_a-zA-Z\[\]\-\!\^\\]([*?.$_a-zA-Z0-9\[\]\-\!\^\\]|::)*
|
|||
<BOTH,SCRIPT,EXPRESSION,MRI>";" { RTOKEN(';');}
|
||||
<BOTH,SCRIPT>"MEMORY" { RTOKEN(MEMORY);}
|
||||
<BOTH,SCRIPT>"REGION_ALIAS" { RTOKEN(REGION_ALIAS);}
|
||||
<BOTH,SCRIPT>"LD_FEATURE" { RTOKEN(LD_FEATURE);}
|
||||
<BOTH,SCRIPT,EXPRESSION>"ORIGIN" { RTOKEN(ORIGIN);}
|
||||
<BOTH,SCRIPT>"VERSION" { RTOKEN(VERSIONK);}
|
||||
<EXPRESSION,BOTH,SCRIPT>"BLOCK" { RTOKEN(BLOCK);}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue