diff options
Diffstat (limited to 'binutils-2.22/ld/ldexp.c')
-rw-r--r-- | binutils-2.22/ld/ldexp.c | 119 |
1 files changed, 79 insertions, 40 deletions
diff --git a/binutils-2.22/ld/ldexp.c b/binutils-2.22/ld/ldexp.c index 68617d8..be296bc 100644 --- a/binutils-2.22/ld/ldexp.c +++ b/binutils-2.22/ld/ldexp.c @@ -1,6 +1,6 @@ /* This module handles expression trees. Copyright 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, - 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 + 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012 Free Software Foundation, Inc. Written by Steve Chamberlain of Cygnus Support <sac@cygnus.com>. @@ -59,7 +59,7 @@ exp_print_token (token_code_type code, int infix_p) static const struct { token_code_type code; - char * name; + const char * name; } table[] = { @@ -156,6 +156,7 @@ exp_intop (bfd_vma value) { etree_type *new_e = (etree_type *) stat_alloc (sizeof (new_e->value)); new_e->type.node_code = INT; + new_e->type.filename = ldlex_filename (); new_e->type.lineno = lineno; new_e->value.value = value; new_e->value.str = NULL; @@ -168,6 +169,7 @@ exp_bigintop (bfd_vma value, char *str) { etree_type *new_e = (etree_type *) stat_alloc (sizeof (new_e->value)); new_e->type.node_code = INT; + new_e->type.filename = ldlex_filename (); new_e->type.lineno = lineno; new_e->value.value = value; new_e->value.str = str; @@ -182,6 +184,7 @@ exp_relop (asection *section, bfd_vma value) { etree_type *new_e = (etree_type *) stat_alloc (sizeof (new_e->rel)); new_e->type.node_code = REL; + new_e->type.filename = ldlex_filename (); new_e->type.lineno = lineno; new_e->type.node_class = etree_rel; new_e->rel.section = section; @@ -210,10 +213,14 @@ new_rel (bfd_vma value, asection *section) static void new_rel_from_abs (bfd_vma value) { + asection *s = expld.section; + + if (s == bfd_abs_section_ptr && expld.phase == lang_final_phase_enum) + s = section_for_dot (); expld.result.valid_p = TRUE; - expld.result.value = value - expld.section->vma; + expld.result.value = value - s->vma; expld.result.str = NULL; - expld.result.section = expld.section; + expld.result.section = s; } static void @@ -404,7 +411,7 @@ fold_binary (etree_type *tree) expld.result.value = ((bfd_signed_vma) lhs.value % (bfd_signed_vma) expld.result.value); else if (expld.phase != lang_mark_phase_enum) - einfo (_("%F%S %% by zero\n")); + einfo (_("%F%S %% by zero\n"), tree->binary.rhs); if (expld.result.section == lhs.section) expld.result.section = NULL; break; @@ -414,7 +421,7 @@ fold_binary (etree_type *tree) expld.result.value = ((bfd_signed_vma) lhs.value / (bfd_signed_vma) expld.result.value); else if (expld.phase != lang_mark_phase_enum) - einfo (_("%F%S / by zero\n")); + einfo (_("%F%S / by zero\n"), tree->binary.rhs); if (expld.result.section == lhs.section) expld.result.section = NULL; break; @@ -587,10 +594,12 @@ fold_name (etree_type *tree) output_section = h->u.def.section->output_section; if (output_section == NULL) { - if (expld.phase != lang_mark_phase_enum) + if (expld.phase == lang_mark_phase_enum) + new_rel (h->u.def.value, h->u.def.section); + else einfo (_("%X%S: unresolvable symbol `%s'" " referenced in expression\n"), - tree->name.name); + tree, tree->name.name); } else if (output_section == bfd_abs_section_ptr && (expld.section != bfd_abs_section_ptr @@ -601,9 +610,11 @@ fold_name (etree_type *tree) output_section); } else if (expld.phase == lang_final_phase_enum - || expld.assigning_to_dot) - einfo (_("%F%S: undefined symbol `%s' referenced in expression\n"), - tree->name.name); + || (expld.phase != lang_mark_phase_enum + && expld.assigning_to_dot)) + einfo (_("%F%S: undefined symbol `%s'" + " referenced in expression\n"), + tree, tree->name.name); else if (h->type == bfd_link_hash_new) { h->type = bfd_link_hash_undefined; @@ -623,8 +634,9 @@ fold_name (etree_type *tree) if (os == NULL) { if (expld.phase == lang_final_phase_enum) - einfo (_("%F%S: undefined section `%s' referenced in expression\n"), - tree->name.name); + einfo (_("%F%S: undefined section `%s'" + " referenced in expression\n"), + tree, tree->name.name); } else if (os->processed_vma) new_rel (0, os->bfd_section); @@ -640,8 +652,9 @@ fold_name (etree_type *tree) if (os == NULL) { if (expld.phase == lang_final_phase_enum) - einfo (_("%F%S: undefined section `%s' referenced in expression\n"), - tree->name.name); + einfo (_("%F%S: undefined section `%s'" + " referenced in expression\n"), + tree, tree->name.name); } else if (os->processed_lma) { @@ -667,11 +680,12 @@ fold_name (etree_type *tree) if (os == NULL) { if (expld.phase == lang_final_phase_enum) - einfo (_("%F%S: undefined section `%s' referenced in expression\n"), - tree->name.name); + einfo (_("%F%S: undefined section `%s'" + " referenced in expression\n"), + tree, tree->name.name); new_number (0); } - else if (os->processed_vma) + else if (os->bfd_section != NULL) { bfd_vma val; @@ -683,6 +697,8 @@ fold_name (etree_type *tree) new_number (val); } + else + new_number (0); } break; @@ -695,7 +711,8 @@ fold_name (etree_type *tree) new_number (mem->length); else einfo (_("%F%S: undefined MEMORY region `%s'" - " referenced in expression\n"), tree->name.name); + " referenced in expression\n"), + tree, tree->name.name); } break; @@ -709,7 +726,8 @@ fold_name (etree_type *tree) new_rel_from_abs (mem->origin); else einfo (_("%F%S: undefined MEMORY region `%s'" - " referenced in expression\n"), tree->name.name); + " referenced in expression\n"), + tree, tree->name.name); } break; @@ -720,7 +738,7 @@ fold_name (etree_type *tree) new_number (config.commonpagesize); else einfo (_("%F%S: unknown constant `%s' referenced in expression\n"), - tree->name.name); + tree, tree->name.name); break; default: @@ -784,15 +802,9 @@ exp_fold_tree_1 (etree_type *tree) if (tree->assign.dst[0] == '.' && tree->assign.dst[1] == 0) { if (tree->type.node_class != etree_assign) - einfo (_("%F%S can not PROVIDE assignment to location counter\n")); - /* After allocation, assignment to dot should not be done inside - an output section since allocation adds a padding statement - that effectively duplicates the assignment. */ - if (expld.phase == lang_mark_phase_enum - || expld.phase == lang_allocating_phase_enum - || ((expld.phase == lang_assigning_phase_enum - || expld.phase == lang_final_phase_enum) - && expld.section == bfd_abs_section_ptr)) + einfo (_("%F%S can not PROVIDE assignment to" + " location counter\n"), tree); + if (expld.phase != lang_first_phase_enum) { /* Notify the folder that this is an assignment to dot. */ expld.assigning_to_dot = TRUE; @@ -802,12 +814,19 @@ exp_fold_tree_1 (etree_type *tree) if (!expld.result.valid_p) { if (expld.phase != lang_mark_phase_enum) - einfo (_("%F%S invalid assignment to location counter\n")); + einfo (_("%F%S invalid assignment to" + " location counter\n"), tree); } else if (expld.dotp == NULL) einfo (_("%F%S assignment to location counter" - " invalid outside of SECTION\n")); - else + " invalid outside of SECTIONS\n"), tree); + + /* After allocation, assignment to dot should not be + done inside an output section since allocation adds a + padding statement that effectively duplicates the + assignment. */ + else if (expld.phase <= lang_allocating_phase_enum + || expld.section == bfd_abs_section_ptr) { bfd_vma nextdot; @@ -819,7 +838,8 @@ exp_fold_tree_1 (etree_type *tree) if (nextdot < expld.dot && expld.section != bfd_abs_section_ptr) einfo (_("%F%S cannot move location counter backwards" - " (from %V to %V)\n"), expld.dot, nextdot); + " (from %V to %V)\n"), + tree, expld.dot, nextdot); else { expld.dot = nextdot; @@ -870,7 +890,7 @@ 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.phase <= lang_mark_phase_enum && tree->type.node_class == etree_assign && tree->assign.hidden)) { @@ -955,6 +975,7 @@ exp_binop (int code, etree_type *lhs, etree_type *rhs) etree_type value, *new_e; value.type.node_code = code; + value.type.filename = lhs->type.filename; value.type.lineno = lhs->type.lineno; value.binary.lhs = lhs; value.binary.rhs = rhs; @@ -974,7 +995,8 @@ exp_trinop (int code, etree_type *cond, etree_type *lhs, etree_type *rhs) etree_type value, *new_e; value.type.node_code = code; - value.type.lineno = lhs->type.lineno; + value.type.filename = cond->type.filename; + value.type.lineno = cond->type.lineno; value.trinary.lhs = lhs; value.trinary.cond = cond; value.trinary.rhs = rhs; @@ -994,6 +1016,7 @@ exp_unop (int code, etree_type *child) etree_type value, *new_e; value.unary.type.node_code = code; + value.unary.type.filename = child->type.filename; value.unary.type.lineno = child->type.lineno; value.unary.child = child; value.unary.type.node_class = etree_unary; @@ -1012,6 +1035,7 @@ exp_nameop (int code, const char *name) etree_type value, *new_e; value.name.type.node_code = code; + value.name.type.filename = ldlex_filename (); value.name.type.lineno = lineno; value.name.name = name; value.name.type.node_class = etree_name; @@ -1036,6 +1060,7 @@ exp_assop (const char *dst, n = (etree_type *) stat_alloc (sizeof (n->assign)); n->assign.type.node_code = '='; + n->assign.type.filename = src->type.filename; n->assign.type.lineno = src->type.lineno; n->assign.type.node_class = class; n->assign.src = src; @@ -1073,6 +1098,7 @@ exp_assert (etree_type *exp, const char *message) n = (etree_type *) stat_alloc (sizeof (n->assert_s)); n->assert_s.type.node_code = '!'; + n->assert_s.type.filename = exp->type.filename; n->assert_s.type.lineno = exp->type.lineno; n->assert_s.type.node_class = etree_assert; n->assert_s.child = exp; @@ -1125,6 +1151,17 @@ exp_print_tree (etree_type *tree) case DATA_SEGMENT_ALIGN: case DATA_SEGMENT_RELRO_END: function_like = TRUE; + break; + case SEGMENT_START: + /* Special handling because arguments are in reverse order and + the segment name is quoted. */ + exp_print_token (tree->type.node_code, FALSE); + fputs (" (\"", config.map_file); + exp_print_tree (tree->binary.rhs); + fputs ("\", ", config.map_file); + exp_print_tree (tree->binary.lhs); + fputc (')', config.map_file); + return; } if (function_like) { @@ -1188,7 +1225,8 @@ exp_get_vma (etree_type *tree, bfd_vma def, char *name) if (expld.result.valid_p) return expld.result.value; else if (name != NULL && expld.phase != lang_mark_phase_enum) - einfo (_("%F%S: nonconstant expression for %s\n"), name); + einfo (_("%F%S: nonconstant expression for %s\n"), + tree, name); } return def; } @@ -1213,7 +1251,8 @@ exp_get_fill (etree_type *tree, fill_type *def, char *name) if (!expld.result.valid_p) { if (name != NULL && expld.phase != lang_mark_phase_enum) - einfo (_("%F%S: nonconstant expression for %s\n"), name); + einfo (_("%F%S: nonconstant expression for %s\n"), + tree, name); return def; } @@ -1272,8 +1311,8 @@ exp_get_abs_int (etree_type *tree, int def, char *name) } else if (name != NULL && expld.phase != lang_mark_phase_enum) { - lineno = tree->type.lineno; - einfo (_("%F%S: nonconstant expression for %s\n"), name); + einfo (_("%F%S: nonconstant expression for %s\n"), + tree, name); } } return def; |