From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 17122 invoked by alias); 1 Jun 2015 20:51:24 -0000 Mailing-List: contact binutils-help@sourceware.org; run by ezmlm Precedence: bulk List-Id: List-Subscribe: List-Archive: List-Post: List-Help: , Sender: binutils-owner@sourceware.org Received: (qmail 16977 invoked by uid 89); 1 Jun 2015 20:51:23 -0000 Authentication-Results: sourceware.org; auth=none X-Virus-Found: No X-Spam-SWARE-Status: No, score=0.9 required=5.0 tests=AWL,BAYES_50,KAM_LAZY_DOMAIN_SECURITY,SPF_HELO_PASS,T_RP_MATCHES_RCVD,UNSUBSCRIBE_BODY autolearn=no version=3.3.2 X-HELO: mx1.redhat.com Received: from mx1.redhat.com (HELO mx1.redhat.com) (209.132.183.28) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with (AES256-GCM-SHA384 encrypted) ESMTPS; Mon, 01 Jun 2015 20:50:23 +0000 Received: from int-mx11.intmail.prod.int.phx2.redhat.com (int-mx11.intmail.prod.int.phx2.redhat.com [10.5.11.24]) by mx1.redhat.com (Postfix) with ESMTPS id D766F2EB649; Mon, 1 Jun 2015 20:50:21 +0000 (UTC) Received: from c64.redhat.com (vpn-230-103.phx2.redhat.com [10.3.230.103]) by int-mx11.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id t51KoE5H030113; Mon, 1 Jun 2015 16:50:21 -0400 From: David Malcolm To: gcc-patches@gcc.gnu.org, binutils@sourceware.org Cc: David Malcolm Subject: [PATCH 10/16] binutils: Introduce "gas_main", and state-purging with "gas" subdir Date: Mon, 01 Jun 2015 20:51:00 -0000 Message-Id: <1433192664-50156-11-git-send-email-dmalcolm@redhat.com> In-Reply-To: <1433192664-50156-1-git-send-email-dmalcolm@redhat.com> References: <1433192664-50156-1-git-send-email-dmalcolm@redhat.com> X-IsSubscribed: yes X-SW-Source: 2015-06/txt/msg00014.txt.bz2 Currently this has only been tested on x86_64, and hardcodes this cleanup: extern void config_obj_elf_c_finalize (void); extern void config_tc_i386_c_finalize (void); Clearly this would need generalizing. gas/ChangeLog: * app.c (app_c_finalize): New function. * as.c: Include new header "libgas.h". (gas_timer): New variable. (emulations): Make the underlying struct emulation be const. (parse_args): Reset internal state of getopt_long_only. (main): Rename to gas_internal_main. Make static. Add param "standalone". Add uses of GAS_TIMER_PUSH and GAS_TIMER_POP. Conditionalize calls to xatexit with check for "standalone", and explicitly call close_output_file in the non-standalone case. Replace calls to xexit with return statements. (config_obj_elf_c_finalize): Add prototype. (config_tc_i386_c_finalize): Likwise. (gas_main): New function. (as_c_finalize): New function. * as.h (app_c_finalize): New prototype. (depend_c_finalize): New prototype. (gas_timer): New variable. (GAS_TIMER_PUSH): New macro. (GAS_TIMER_POP): New macro. * asmain.c: New file. * config/obj-elf.c (obj_elf_ident): Split out the function-level static variable "comment_section" into... (obj_elf_ident_comment_section): ...this file-level static variable. (config_obj_elf_c_finalize): New function. * config/tc-i386.c (config_tc_i386_c_finalize): New function. * depend.c (depend_c_finalize): New function. * dw2gencfi.c (dw2gencfi_c_finalize): New function. * dw2gencfi.h (dw2gencfi_c_finalize): New prototype. * libgas.h: New file. * macro.c (macro_c_finalize): New function. * macro.h (macro_c_finalize): New prototype. * output-file.c (output_file_c_finalize): New function. * output-file.h (output_file_c_finalize): New prototype. * read.c (read_c_finalize): New function. * read.h (read_c_finalize): New prototype. * subsegs.c (subsegs_c_finalize): New function. * subsegs.h (subsegs_c_finalize): New prototype. * symbols.c (symbols_c_finalize): New function. * symbols.h (symbols_c_finalize): New prototype. * write.c (write_c_finalize): New function. * write.h (write_c_finalize): New prototype. --- gas/app.c | 27 ++++++++ gas/as.c | 182 ++++++++++++++++++++++++++++++++++++++++++++++++--- gas/as.h | 12 ++++ gas/asmain.c | 35 ++++++++++ gas/config/obj-elf.c | 25 +++++-- gas/config/tc-i386.c | 79 ++++++++++++++++++++++ gas/depend.c | 10 +++ gas/dw2gencfi.c | 12 ++++ gas/dw2gencfi.h | 2 + gas/libgas.h | 41 ++++++++++++ gas/macro.c | 18 +++++ gas/macro.h | 2 + gas/output-file.c | 8 +++ gas/output-file.h | 1 + gas/read.c | 47 +++++++++++++ gas/read.h | 2 + gas/subsegs.c | 10 +++ gas/subsegs.h | 1 + gas/symbols.c | 41 ++++++++++++ gas/symbols.h | 2 + gas/write.c | 15 +++++ gas/write.h | 1 + 22 files changed, 558 insertions(+), 15 deletions(-) create mode 100644 gas/asmain.c create mode 100644 gas/libgas.h diff --git a/gas/app.c b/gas/app.c index 67402e2..fda8216 100644 --- a/gas/app.c +++ b/gas/app.c @@ -1479,3 +1479,30 @@ do_scrub_chars (size_t (*get) (char *, size_t), char *tostart, size_t tolen) return to - tostart; } + +/* Reset all global state within app.c. */ + +void +app_c_finalize (void) +{ +#ifdef H_TICK_HEX + enable_h_tick_hex = 0; +#endif +#ifdef TC_M68K + scrub_m68k_mri = 0; +#endif +#if defined TC_ARM && defined OBJ_ELF + symver_state = NULL; +#endif + CLEAR_VAR (lex); + state = 0; + old_state = 0; + out_string = NULL; + CLEAR_VAR (out_buf); + add_newlines = 0; + saved_input = NULL; + saved_input_len = 0; + CLEAR_VAR (input_buffer); + mri_state = NULL; + mri_last_ch = 0; +} diff --git a/gas/as.c b/gas/as.c index 2a8923f..90dc298 100644 --- a/gas/as.c +++ b/gas/as.c @@ -31,6 +31,8 @@ #define COMMON +#include "libgas.h" + #include "as.h" #include "subsegs.h" #include "output-file.h" @@ -66,6 +68,8 @@ struct defsym_list valueT value; }; +/* Global timer. */ +struct ctimer *gas_timer; /* True if a listing is wanted. */ int listing; @@ -135,7 +139,7 @@ extern struct emulation mipsbelf, mipslelf, mipself; extern struct emulation i386coff, i386elf, i386aout; extern struct emulation crisaout, criself; -static struct emulation *const emulations[] = { EMULATIONS }; +static const struct emulation *const emulations[] = { EMULATIONS }; static const int n_emulations = sizeof (emulations) / sizeof (emulations[0]); static void @@ -546,6 +550,9 @@ parse_args (int * pargc, char *** pargv) new_argc = 1; new_argv[new_argc] = NULL; + /* Reset internal state of getopt_long_only. */ + optind = 0; + while (1) { /* getopt_long_only is like getopt_long, but '-' as well as '--' can @@ -1122,13 +1129,18 @@ perform_an_assembly_pass (int argc, char ** argv) } -int -main (int argc, char ** argv) +/* Run the assembler: almost the top-level of the assembler implementation. + Called by gas_main after it has set up gas_timer. */ + +static int +gas_internal_main (int argc, char ** argv, int standalone) { char ** argv_orig = argv; int macro_strip_at; + GAS_TIMER_PUSH ("before pass"); + start_time = get_run_time (); #ifdef HAVE_SBRK start_sbrk = (char *) sbrk (0); @@ -1183,9 +1195,10 @@ main (int argc, char ** argv) expr_begin (); /* It has to be called after dump_statistics (). */ - xatexit (close_output_file); + if (standalone) + xatexit (close_output_file); - if (flag_print_statistics) + if (flag_print_statistics && standalone) xatexit (dump_statistics); macro_strip_at = 0; @@ -1236,8 +1249,14 @@ main (int argc, char ** argv) PROGRESS (1); + GAS_TIMER_POP (); + /* Assemble it. */ + GAS_TIMER_PUSH ("perform_an_assembly_pass"); perform_an_assembly_pass (argc, argv); + GAS_TIMER_POP (); + + GAS_TIMER_PUSH ("after pass"); cond_finish_check (-1); @@ -1316,13 +1335,158 @@ main (int argc, char ** argv) END_PROGRESS (myname); - /* Use xexit instead of return, because under VMS environments they - may not place the same interpretation on the value given. */ + if (!standalone) + close_output_file (); + + GAS_TIMER_POP (); + if (had_errors () != 0) - xexit (EXIT_FAILURE); + return EXIT_FAILURE; /* Only generate dependency file if assembler was successful. */ print_dependencies (); - xexit (EXIT_SUCCESS); + return EXIT_SUCCESS; +} + +static void as_c_finalize (void); + +/* FIXME. */ +extern void config_obj_elf_c_finalize (void); +extern void config_tc_i386_c_finalize (void); + +/* Public API entrypoint. */ + +int +gas_main (int argc, char **argv, int standalone, struct ctimer *timer) +{ + int result; + + /* Set global gas_timer. */ + gas_timer = timer; + + GAS_TIMER_PUSH ("gas_main"); + + result = gas_internal_main (argc, argv, standalone); + if (!standalone) + { + GAS_TIMER_PUSH ("cleanup"); + + if (flag_print_statistics) + dump_statistics (); + + /* Restore all state. */ + bfd_uninit (); + + /* Restore all state within gas. */ + app_c_finalize (); + as_c_finalize (); + depend_c_finalize (); + dw2gencfi_c_finalize (); + macro_c_finalize (); + read_c_finalize (); + output_file_c_finalize (); + subsegs_c_finalize (); + symbols_c_finalize (); + write_c_finalize (); + /* FIXME: */ + config_obj_elf_c_finalize (); + config_tc_i386_c_finalize (); + + GAS_TIMER_POP (); + } + + GAS_TIMER_POP (); + + gas_timer = NULL; + + return result; +} + +/* Reset all global state within as.c. */ + +static void +as_c_finalize (void) +{ + listing = 0; + debug_type = DEBUG_UNSPECIFIED; + use_gnu_debug_info_extensions = 0; + max_macro_nest = 100; + myname = NULL; + chunksize = 0; + debug_memory = 0; + verbose = 0; + keep_it = 0; + reg_section = NULL; + expr_section = NULL; + text_section = NULL; + data_section = NULL; + bss_section = NULL; + listing_filename = NULL; + defsyms = NULL; +#ifdef HAVE_ITBL_CPU + itbl_files = NULL; +#endif + start_time = 0; +#ifdef HAVE_SBRK + start_sbrk = NULL; +#endif + flag_macro_alternate = 0; + + /* The header files use the prefix COMMON for various declarations, + which for most translation units is "extern". + Within as.c, COMMON is empty, and so this file contains + their definitions. + Reset their state here. */ + + /* "COMMON" vars within as.h. */ + now_subseg = 0; + now_seg = NULL; + flag_no_comments = 0; + flag_debug = 0; + flag_signed_overflow_ok = 0; +#ifndef WORKING_DOT_WORD + flag_warn_displacement = 0; +#endif + flag_keep_locals = 0; + flag_mri = 0; + flag_readonly_data_in_text = 0; + flag_no_warnings = 0; + flag_fatal_warnings = 0; + flag_always_generate_output = 0; + flag_print_statistics = 0; + flag_strip_local_absolute = 0; + flag_traditional_format = 0; + flag_compress_debug = 0; + flag_execstack = 0; + flag_noexecstack = 0; + out_file_name = NULL; + insttbl_file_name = NULL; + need_pass_2 = 0; + linkrelax = 0; + flag_dwarf_sections = 0; +#ifdef TC_M68K + flag_m68k_mri = 0; +#endif +#ifdef WARN_COMMENTS + warn_comment = 0; + found_comment = 0; + found_comment_file = NULL; +#endif +#if defined OBJ_ELF || defined OBJ_MAYBE_ELF + flag_size_check = 0; +#endif + + /* "COMMON" var within emul.h. */ +#ifdef USE_EMULATIONS + this_emulation = NULL; +#endif + + /* "COMMON" vars within frags.h. */ + frag_now = NULL; + CLEAR_VAR (zero_address_frag); + CLEAR_VAR (predefined_address_frag); + + /* "COMMON" var within obj.h. */ + this_format = NULL; } diff --git a/gas/as.h b/gas/as.h index 6de319e..8e241a9 100644 --- a/gas/as.h +++ b/gas/as.h @@ -517,6 +517,9 @@ void register_dependency (char *); void print_dependencies (void); segT subseg_get (const char *, int); +extern void app_c_finalize (void); +extern void depend_c_finalize (void); + const char *remap_debug_filename (const char *); void add_debug_prefix_map (const char *); @@ -631,4 +634,13 @@ flag_size_check; #error "Octets per byte conflicts with its power-of-two definition!" #endif +extern struct ctimer *gas_timer; + +#define GAS_TIMER_PUSH(ITEM_NAME) \ + do { CTIMER_PUSH (gas_timer, (ITEM_NAME)); } while (0) + +#define GAS_TIMER_POP() \ + do { CTIMER_POP (gas_timer); } while (0) + + #endif /* GAS */ diff --git a/gas/asmain.c b/gas/asmain.c new file mode 100644 index 0000000..687ae73 --- /dev/null +++ b/gas/asmain.c @@ -0,0 +1,35 @@ +/* asmain.c - "main" for standalone "as" program. + Copyright (C) 2015 Free Software Foundation, Inc. + + This file is part of GAS, the GNU Assembler. + + GAS is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3, or (at your option) + any later version. + + GAS is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public + License for more details. + + You should have received a copy of the GNU General Public License + along with GAS; see the file COPYING. If not, write to the Free + Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA + 02110-1301, USA. */ + +#include "as.h" +#include "libgas.h" + +int +main (int argc, char ** argv) +{ + int result = gas_main (argc, + argv, + 1, /* standalone */ + NULL); /* timer */ + + /* Use xexit instead of return, because under VMS environments they + may not place the same interpretation on the value given. */ + xexit (result); +} diff --git a/gas/config/obj-elf.c b/gas/config/obj-elf.c index 4d7a8a7..cb44a10 100644 --- a/gas/config/obj-elf.c +++ b/gas/config/obj-elf.c @@ -1947,10 +1947,11 @@ obj_elf_type (int ignore ATTRIBUTE_UNUSED) demand_empty_rest_of_line (); } +static segT obj_elf_ident_comment_section; + static void obj_elf_ident (int ignore ATTRIBUTE_UNUSED) { - static segT comment_section; segT old_section = now_seg; int old_subsection = now_subseg; @@ -1958,14 +1959,14 @@ obj_elf_ident (int ignore ATTRIBUTE_UNUSED) md_flush_pending_output (); #endif - if (!comment_section) + if (!obj_elf_ident_comment_section) { char *p; - comment_section = subseg_new (".comment", 0); - bfd_set_section_flags (stdoutput, comment_section, + obj_elf_ident_comment_section = subseg_new (".comment", 0); + bfd_set_section_flags (stdoutput, obj_elf_ident_comment_section, SEC_READONLY | SEC_HAS_CONTENTS | SEC_MERGE | SEC_STRINGS); - comment_section->entsize = 1; + obj_elf_ident_comment_section->entsize = 1; #ifdef md_elf_section_change_hook md_elf_section_change_hook (); #endif @@ -1973,7 +1974,7 @@ obj_elf_ident (int ignore ATTRIBUTE_UNUSED) *p = 0; } else - subseg_set (comment_section, 0); + subseg_set (obj_elf_ident_comment_section, 0); stringer (8 + 1); subseg_set (old_section, old_subsection); } @@ -2681,3 +2682,15 @@ const struct format_ops elf_format_ops = 0, elf_adjust_symtab }; + +/* FIXME. */ +extern void config_obj_elf_c_finalize (void); + +/* Reset all global state within this source file. */ + +void +config_obj_elf_c_finalize (void) +{ + obj_elf_ident_comment_section = NULL; + /* TODO: anything else? */ +} diff --git a/gas/config/tc-i386.c b/gas/config/tc-i386.c index db263ee..cbc6e13 100644 --- a/gas/config/tc-i386.c +++ b/gas/config/tc-i386.c @@ -10655,3 +10655,82 @@ handle_large_common (int small ATTRIBUTE_UNUSED) } } #endif /* OBJ_ELF || OBJ_MAYBE_ELF */ + +/* FIXME. */ +extern void config_tc_i386_c_finalize (void); + +/* Reset all global state within this source file. */ + +void +config_tc_i386_c_finalize (void) +{ +#ifdef TE_LINUX + flag_compress_debug = COMPRESS_DEBUG_ZLIB; +#endif + default_arch = DEFAULT_ARCH; + CLEAR_VAR (rc_op); + CLEAR_VAR (mask_op); + CLEAR_VAR (broadcast_op); + CLEAR_VAR (i); + current_templates = NULL; + CLEAR_VAR (disp_expressions); + CLEAR_VAR (im_expressions); + this_operand = -1; + flag_code = 0; + object_64bit = 0; + disallow_64bit_reloc = 0; + use_rela_relocations = 0; +#if ((defined (OBJ_MAYBE_COFF) && defined (OBJ_MAYBE_AOUT)) \ + || defined (OBJ_ELF) || defined (OBJ_MAYBE_ELF) \ + || defined (TE_PE) || defined (TE_PEP) || defined (OBJ_MACH_O)) + x86_elf_abi = I386_ABI; +#endif +#if defined (TE_PE) || defined (TE_PEP) + use_big_obj = 0; +#endif +#if defined (OBJ_ELF) || defined (OBJ_MAYBE_ELF) + no_shared = 0; +#endif + intel_syntax = 0; + intel_mnemonic = !SYSV386_COMPAT; + old_gcc = OLDGCC_COMPAT; + allow_pseudo_reg = 0; + allow_naked_reg = 0; + add_bnd_prefix = 0; + allow_index_reg = 0; + omit_lock_prefix = 0; + operand_check = check_warning; + register_prefix = "%"; + stackop_size = '\0'; + optimize_align_code = 1; + quiet_warnings = 0; + cpu_arch_name = NULL; + cpu_sub_arch_name = NULL; + //cpu_arch_flags = CPU_UNKNOWN_FLAGS; + cpu_arch_tune_set = 0; + cpu_arch_tune = PROCESSOR_UNKNOWN; + CLEAR_VAR (cpu_arch_tune_flags); + cpu_arch_isa = PROCESSOR_UNKNOWN; + CLEAR_VAR (cpu_arch_isa_flags); + no_cond_jump_promotion = 0; + sse2avx = 0; + avxscalar = 0; + evexlig = 0; + evexwig = 0; + evexrcig = rne; + GOT_symbol = NULL; + x86_dwarf2_return_column = 0; + x86_cie_data_alignment = 0; + input_line_pointer = NULL; + if (op_hash) + { + hash_die (op_hash); + op_hash = NULL; + } + if (reg_hash) + { + hash_die (reg_hash); + reg_hash= NULL; + } + cons_sign = -1; +} diff --git a/gas/depend.c b/gas/depend.c index 1a1ec63..cc8a3e0 100644 --- a/gas/depend.c +++ b/gas/depend.c @@ -205,3 +205,13 @@ print_dependencies (void) if (fclose (f)) as_warn (_("can't close `%s'"), dep_file); } + +/* Reset all global state within depend.c. */ + +void +depend_c_finalize (void) +{ + dep_file = NULL; + dep_chain = NULL; + column = 0; +} diff --git a/gas/dw2gencfi.c b/gas/dw2gencfi.c index ef97e18..1527624 100644 --- a/gas/dw2gencfi.c +++ b/gas/dw2gencfi.c @@ -2084,3 +2084,15 @@ cfi_finish (void) { } #endif /* TARGET_USE_CFIPOP */ + +/* Reset all global state within dw2gencfi.c. */ + +void +dw2gencfi_c_finalize (void) +{ + dwcfi_hash = NULL; + all_fde_data = NULL; + last_fde_data = &all_fde_data; + cie_root = NULL; + cfi_sections = CFI_EMIT_eh_frame; +} diff --git a/gas/dw2gencfi.h b/gas/dw2gencfi.h index 6e2c50e..009eee3 100644 --- a/gas/dw2gencfi.h +++ b/gas/dw2gencfi.h @@ -133,4 +133,6 @@ extern struct fde_entry *all_fde_data; #define CFI_val_encoded_addr 0x105 #define CFI_label 0x106 +extern void dw2gencfi_c_finalize (void); + #endif /* DW2GENCFI_H */ diff --git a/gas/libgas.h b/gas/libgas.h new file mode 100644 index 0000000..479a990 --- /dev/null +++ b/gas/libgas.h @@ -0,0 +1,41 @@ +/* API for the GNU Assembler. + Copyright (C) 2015 Free Software Foundation, Inc. + + This file is part of the GNU Binutils. + + 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 + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, + MA 02110-1301, USA. */ + +#ifndef LIBGAS_H +#define LIBGAS_H + +#ifdef __cplusplus +extern "C" { +#endif + +struct ctimer; + +extern int +gas_main (int argc, + char **argv, + int standalone, + struct ctimer *timer); + +#ifdef __cplusplus +} +#endif + + +#endif /* ! defined (LIBGAS_H) */ diff --git a/gas/macro.c b/gas/macro.c index 119b1bf..76e8fdf 100644 --- a/gas/macro.c +++ b/gas/macro.c @@ -1401,3 +1401,21 @@ expand_irp (int irpc, size_t idx, sb *in, sb *out, size_t (*get_line) (sb *)) return err; } + +/* Reset all global state within macro.c. */ + +void +macro_c_finalize (void) +{ + if (macro_hash) + { + hash_die (macro_hash); + macro_hash = NULL; + } + macro_defined = 0; + macro_alternate = 0; + macro_mri = 0; + macro_strip_at = 0; + macro_expr = 0; + macro_number = 0; +} diff --git a/gas/macro.h b/gas/macro.h index 46b1575..a0c48c3 100644 --- a/gas/macro.h +++ b/gas/macro.h @@ -93,4 +93,6 @@ extern int check_macro (const char *, sb *, const char **, macro_entry **); extern void delete_macro (const char *); extern const char *expand_irp (int, size_t, sb *, sb *, size_t (*) (sb *)); +extern void macro_c_finalize (void); + #endif diff --git a/gas/output-file.c b/gas/output-file.c index 94dbc2e..769bd43 100644 --- a/gas/output-file.c +++ b/gas/output-file.c @@ -71,3 +71,11 @@ output_file_close (char *filename) as_fatal (_("can't close %s: %s"), filename, bfd_errmsg (bfd_get_error ())); } + +/* Reset all global state within output-file.c. */ + +void +output_file_c_finalize (void) +{ + stdoutput = NULL; +} diff --git a/gas/output-file.h b/gas/output-file.h index bfba284..3e8d848 100644 --- a/gas/output-file.h +++ b/gas/output-file.h @@ -21,5 +21,6 @@ void output_file_append (char *where, long length, char *filename); void output_file_close (char *filename); void output_file_create (char *name); +void output_file_c_finalize (void); /* end of output-file.h */ diff --git a/gas/read.c b/gas/read.c index 2224c0e..d49b122 100644 --- a/gas/read.c +++ b/gas/read.c @@ -6170,3 +6170,50 @@ find_end_of_line (char *s, int mri_string) { return _find_end_of_line (s, mri_string, 0, 0); } + +/* Reset all global state within read.c. */ + +void +read_c_finalize (void) +{ + input_line_pointer = NULL; + /* FIXME: char lex_type[256] = { */ + /* FIXME:char is_end_of_line[256] = { */ +#ifndef TC_CASE_SENSITIVE + CLEAR_VAR (original_case_string); +#endif + buffer = NULL; + buffer_limit = NULL; + target_big_endian = TARGET_BYTES_BIG_ENDIAN; + include_dirs = NULL; + include_dir_count = 0; + include_dir_maxlen = 1; +#ifndef WORKING_DOT_WORD + broken_words = NULL; + new_broken_words = 0; +#endif + abs_section_offset = 0; + line_label = NULL; + mri_common_symbol = NULL; + mri_pending_align = 0; +#ifndef NO_LISTING +#ifdef OBJ_ELF + dwarf_file_string = 0; +#endif +#endif +#ifdef HANDLE_BUNDLE + bundle_align_p2 = 0; + bundle_lock_frag = NULL; + bundle_lock_frchain = NULL; + bundle_lock_depth = 0; +#endif + if (po_hash) + { + hash_die (po_hash); + po_hash = NULL; + } + pop_override_ok = 0; + pop_table_name = NULL; + scrub_string = NULL; + scrub_string_end = NULL; +} diff --git a/gas/read.h b/gas/read.h index d7ac6ce..7d17a7a 100644 --- a/gas/read.h +++ b/gas/read.h @@ -198,3 +198,5 @@ extern void s_xstab (int what); extern void s_rva (int); extern void s_incbin (int); extern void s_weakref (int); + +extern void read_c_finalize (void); diff --git a/gas/subsegs.c b/gas/subsegs.c index 4e422de..331ec29 100644 --- a/gas/subsegs.c +++ b/gas/subsegs.c @@ -325,4 +325,14 @@ subsegs_print_statistics (FILE *file) } } +/* Reset all global state within subsegs.c. */ + +void +subsegs_c_finalize (void) +{ + frchain_now = NULL; + obstack_free (&frchains, 0); + CLEAR_VAR (dummy_frag); +} + /* end of subsegs.c */ diff --git a/gas/subsegs.h b/gas/subsegs.h index 82837a3..78e5b2f 100644 --- a/gas/subsegs.h +++ b/gas/subsegs.h @@ -117,3 +117,4 @@ typedef struct segment_info_struct { extern symbolS *section_symbol (segT); extern void subsegs_print_statistics (FILE *); +extern void subsegs_c_finalize (void); diff --git a/gas/symbols.c b/gas/symbols.c index 07362bb..d660d53 100644 --- a/gas/symbols.c +++ b/gas/symbols.c @@ -3248,3 +3248,44 @@ symbol_relc_make_expr (expressionS * exp) } #endif + +/* Reset all global state within symbols.c. */ + +void +symbols_c_finalize (void) +{ + symbols_case_sensitive = 1; + if (sy_hash) + { + hash_die (sy_hash); + sy_hash = NULL; + } + if (local_hash) + { + hash_die (local_hash); + local_hash = NULL; + } + symbol_rootP = NULL; + symbol_lastP = NULL; + CLEAR_VAR (abs_symbol); + CLEAR_VAR (dot_symbol); + obstack_free (¬es, 0); + CLEAR_VAR (notes); +#ifdef TE_PE + an_external_name = NULL; +#endif + local_symbol_count = 0; + local_symbol_conversion_count = 0; + dollar_labels = NULL; + dollar_label_instances = NULL; + dollar_label_defines = NULL; + dollar_label_count = 0; + dollar_label_max = 0; + CLEAR_VAR (fb_low_counter); + fb_labels = NULL; + fb_label_instances = NULL; + fb_label_count = 0; + fb_label_max = 0; + indent_level = 0; + max_indent_level = 8; +} diff --git a/gas/symbols.h b/gas/symbols.h index cf4f30f..8a88383 100644 --- a/gas/symbols.h +++ b/gas/symbols.h @@ -213,3 +213,5 @@ void symbol_set_obj (symbolS *, OBJ_SYMFIELD_TYPE *); TC_SYMFIELD_TYPE *symbol_get_tc (symbolS *); void symbol_set_tc (symbolS *, TC_SYMFIELD_TYPE *); #endif + +extern void symbols_c_finalize (void); diff --git a/gas/write.c b/gas/write.c index bc76962..9562a7b 100644 --- a/gas/write.c +++ b/gas/write.c @@ -2907,3 +2907,18 @@ print_fixup (fixS *fixp) TC_FIX_DATA_PRINT (stderr, fixp); #endif } + +/* Reset all global state within write.c. */ + +void +write_c_finalize (void) +{ + finalize_syms = 0; + symbol_table_frozen = 0; + abs_section_sym = NULL; + dot_value = 0; + dot_frag = NULL; + reloc_list = NULL; + frags_chained = 0; + n_fixups = 0; +} diff --git a/gas/write.h b/gas/write.h index e0b5b36..63026f9 100644 --- a/gas/write.h +++ b/gas/write.h @@ -184,5 +184,6 @@ extern fixS *fix_new_exp (fragS * frag, int where, int size, expressionS *exp, int pcrel, bfd_reloc_code_real_type r_type); extern void write_print_statistics (FILE *); +extern void write_c_finalize (void); #endif /* __write_h__ */ -- 1.8.5.3