diff options
author | Iain Sandoe <iain@codesourcery.com> | 2012-02-21 13:39:37 +0000 |
---|---|---|
committer | Iain Sandoe <iain@codesourcery.com> | 2012-02-21 13:39:37 +0000 |
commit | 16a87420985f256b5cde070586ebcdfda2225b01 (patch) | |
tree | 8d56cb791213e8329675be59b24b693bfbb4aea6 | |
parent | 025682772a5d4ce0877e3bcbb63086c1883c7211 (diff) | |
download | gdb-16a87420985f256b5cde070586ebcdfda2225b01.zip gdb-16a87420985f256b5cde070586ebcdfda2225b01.tar.gz gdb-16a87420985f256b5cde070586ebcdfda2225b01.tar.bz2 |
provide a hook to allow checking errors just before we output the file.
gas:
* write.c (write_object_file): Add md_pre_output_hook.
* config/obj-macho.c (obj_mach_o_check_before_writing): New.
(obj_mach_o_pre_output_hook): New.
* config/obj-macho.h (md_pre_output_hook): Define.
(obj_mach_o_pre_output_hook): Declare.
-rw-r--r-- | gas/ChangeLog | 8 | ||||
-rw-r--r-- | gas/config/obj-macho.c | 66 | ||||
-rw-r--r-- | gas/config/obj-macho.h | 3 | ||||
-rw-r--r-- | gas/write.c | 4 |
4 files changed, 81 insertions, 0 deletions
diff --git a/gas/ChangeLog b/gas/ChangeLog index 7a8fcb5..63f341e 100644 --- a/gas/ChangeLog +++ b/gas/ChangeLog @@ -1,3 +1,11 @@ +2012-02-21 Iain Sandoe <idsandoe@googlemail.com> + + * write.c (write_object_file): Add md_pre_output_hook. + * config/obj-macho.c (obj_mach_o_check_before_writing): New. + (obj_mach_o_pre_output_hook): New. + * config/obj-macho.h (md_pre_output_hook): Define. + (obj_mach_o_pre_output_hook): Declare. + 2012-02-21 Tristan Gingold <gingold@adacore.com> * config/tc-i386.h (OBJ_MACH_O): New section. diff --git a/gas/config/obj-macho.c b/gas/config/obj-macho.c index 376e620..21281a0 100644 --- a/gas/config/obj-macho.c +++ b/gas/config/obj-macho.c @@ -1554,6 +1554,72 @@ obj_mach_o_process_stab (int what, const char *string, /* It's a debug symbol. */ s->symbol.flags |= BSF_DEBUGGING; + + /* We've set it - so check it, if you can, but don't try to create the + flags. */ + s->symbol.udata.i = SYM_MACHO_FIELDS_NOT_VALIDATED; +} + +/* This is a place to check for any errors that we can't detect until we know + what remains undefined at the end of assembly. */ + +static void +obj_mach_o_check_before_writing (bfd *abfd ATTRIBUTE_UNUSED, + asection *sec, + void *unused ATTRIBUTE_UNUSED) +{ + fixS *fixP; + struct frchain *frchp; + segment_info_type *seginfo = seg_info (sec); + + if (seginfo == NULL) + return; + + /* We are not allowed subtractions where either of the operands is + undefined. So look through the frags for any fixes to check. */ + for (frchp = seginfo->frchainP; frchp != NULL; frchp = frchp->frch_next) + for (fixP = frchp->fix_root; fixP != NULL; fixP = fixP->fx_next) + { + if (fixP->fx_addsy != NULL + && fixP->fx_subsy != NULL + && (! S_IS_DEFINED (fixP->fx_addsy) + || ! S_IS_DEFINED (fixP->fx_subsy))) + { + segT add_symbol_segment = S_GET_SEGMENT (fixP->fx_addsy); + segT sub_symbol_segment = S_GET_SEGMENT (fixP->fx_subsy); + + if (! S_IS_DEFINED (fixP->fx_addsy) + && S_IS_DEFINED (fixP->fx_subsy)) + { + as_bad_where (fixP->fx_file, fixP->fx_line, + _("`%s' can't be undefined in `%s' - `%s' {%s section}"), + S_GET_NAME (fixP->fx_addsy), S_GET_NAME (fixP->fx_addsy), + S_GET_NAME (fixP->fx_subsy), segment_name (sub_symbol_segment)); + } + else if (! S_IS_DEFINED (fixP->fx_subsy) + && S_IS_DEFINED (fixP->fx_addsy)) + { + as_bad_where (fixP->fx_file, fixP->fx_line, + _("`%s' can't be undefined in `%s' {%s section} - `%s'"), + S_GET_NAME (fixP->fx_subsy), S_GET_NAME (fixP->fx_addsy), + segment_name (add_symbol_segment), S_GET_NAME (fixP->fx_subsy)); + } + else + { + as_bad_where (fixP->fx_file, fixP->fx_line, + _("`%s' and `%s' can't be undefined in `%s' - `%s'"), + S_GET_NAME (fixP->fx_addsy), S_GET_NAME (fixP->fx_subsy), + S_GET_NAME (fixP->fx_addsy), S_GET_NAME (fixP->fx_subsy)); + } + } + } +} + +/* Do any checks that we can't complete without knowing what's undefined. */ +void +obj_mach_o_pre_output_hook (void) +{ + bfd_map_over_sections (stdoutput, obj_mach_o_check_before_writing, (char *) 0); } /* Here we count up frags in each subsection (where a sub-section is defined diff --git a/gas/config/obj-macho.h b/gas/config/obj-macho.h index 0ac8df4..92cb8ef 100644 --- a/gas/config/obj-macho.h +++ b/gas/config/obj-macho.h @@ -87,6 +87,9 @@ struct obj_mach_o_frag_data #define OBJ_FRAG_TYPE struct obj_mach_o_frag_data +#define md_pre_output_hook obj_mach_o_pre_output_hook() +extern void obj_mach_o_pre_output_hook(void); + #define md_pre_relax_hook obj_mach_o_pre_relax_hook() extern void obj_mach_o_pre_relax_hook (void); diff --git a/gas/write.c b/gas/write.c index f640c61..23d4334 100644 --- a/gas/write.c +++ b/gas/write.c @@ -1767,6 +1767,10 @@ write_object_file (void) fragS *fragP; /* Track along all frags. */ #endif +#ifdef md_pre_output_hook + md_pre_output_hook; +#endif + /* Do we really want to write it? */ { int n_warns, n_errs; |