From 1002d8ed0b06cebde9e23c04ca1d2475854f2b93 Mon Sep 17 00:00:00 2001 From: Doug Evans Date: Mon, 12 Jan 1998 21:12:52 +0000 Subject: [PATCH] * cgen.c: #include setjmp.h. Clean up pass over `struct foo' usage. (expr_jmp_buf): New static local. (cgen_parse_operand): Allow use of longjmp in parsing to handle errors. (cgen_md_operand): New function. * tc-m32r.c: Clean up pass over `struct foo' usage. (md_estimate_size_before_relax): Use CGEN_INSN_MNEMONIC. --- gas/ChangeLog | 9 ++++++++ gas/cgen.c | 64 ++++++++++++++++++++++++++++++++++++++------------- 2 files changed, 57 insertions(+), 16 deletions(-) diff --git a/gas/ChangeLog b/gas/ChangeLog index 8689ef42d4..d1582ec214 100644 --- a/gas/ChangeLog +++ b/gas/ChangeLog @@ -1,3 +1,12 @@ +Mon Jan 12 13:04:57 1998 Doug Evans + + * cgen.c: #include setjmp.h. Clean up pass over `struct foo' usage. + (expr_jmp_buf): New static local. + (cgen_parse_operand): Allow use of longjmp in parsing to handle errors. + (cgen_md_operand): New function. + * tc-m32r.c: Clean up pass over `struct foo' usage. + (md_estimate_size_before_relax): Use CGEN_INSN_MNEMONIC. + Tue Jan 6 15:36:02 1998 Richard Henderson * symbols.c (S_SET_SEGMENT): Don't set the segment for section syms. diff --git a/gas/cgen.c b/gas/cgen.c index 3ed8d99b98..0e5c33c4ac 100644 --- a/gas/cgen.c +++ b/gas/cgen.c @@ -17,6 +17,7 @@ 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, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ +#include #include "ansidecl.h" #include "bfd.h" #include "cgen-opc.h" @@ -103,9 +104,9 @@ fixS * cgen_record_fixup (frag, where, insn, length, operand, opinfo, symbol, offset) fragS *frag; int where; - const struct cgen_insn *insn; + const CGEN_INSN *insn; int length; - const struct cgen_operand *operand; + const CGEN_OPERAND *operand; int opinfo; symbolS *symbol; offsetT offset; @@ -141,9 +142,9 @@ fixS * cgen_record_fixup_exp (frag, where, insn, length, operand, opinfo, exp) fragS *frag; int where; - const struct cgen_insn *insn; + const CGEN_INSN *insn; int length; - const struct cgen_operand *operand; + const CGEN_OPERAND *operand; int opinfo; expressionS *exp; { @@ -161,6 +162,9 @@ cgen_record_fixup_exp (frag, where, insn, length, operand, opinfo, exp) return fixP; } +/* Used for communication between the next two procedures. */ +static jmp_buf expr_jmp_buf; + /* Callback for cgen interface. Parse the expression at *STRP. The result is an error message or NULL for success (in which case *STRP is advanced past the parsed text). @@ -181,7 +185,14 @@ cgen_parse_operand (want, strP, opindex, opinfo, resultP, valueP) enum cgen_parse_operand_result *resultP; bfd_vma *valueP; { - char *hold; +#ifdef __STDC__ + /* These is volatile to survive the setjmp. */ + char * volatile hold; + enum cgen_parse_operand_result * volatile resultP_1; +#else + static char *hold; + static enum cgen_parse_operand_result *resultP_1; +#endif const char *errmsg = NULL; expressionS exp; @@ -191,9 +202,21 @@ cgen_parse_operand (want, strP, opindex, opinfo, resultP, valueP) return NULL; } + resultP_1 = resultP; hold = input_line_pointer; input_line_pointer = (char *) *strP; + + /* We rely on md_operand to longjmp back to us. + This is done via cgen_md_operand. */ + if (setjmp (expr_jmp_buf) != 0) + { + input_line_pointer = (char *) hold; + *resultP_1 = CGEN_PARSE_OPERAND_RESULT_ERROR; + return "illegal operand"; + } + expression (&exp); + *strP = input_line_pointer; input_line_pointer = hold; @@ -227,13 +250,25 @@ cgen_parse_operand (want, strP, opindex, opinfo, resultP, valueP) return errmsg; } +/* md_operand handler to catch unrecognized expressions and halt the + parsing process so the next entry can be tried. + + ??? This could be done differently by adding code to `expression'. */ + +void +cgen_md_operand (expressionP) + expressionS *expressionP; +{ + longjmp (expr_jmp_buf, 1); +} + /* Finish assembling instruction INSN. BUF contains what we've built up so far. LENGTH is the size of the insn in bits. */ void cgen_asm_finish_insn (insn, buf, length) - const struct cgen_insn *insn; + const CGEN_INSN *insn; cgen_insn_t *buf; unsigned int length; { @@ -303,12 +338,9 @@ cgen_asm_finish_insn (insn, buf, length) f); /* Record the operand number with the fragment so md_convert_frag can use cgen_md_record_fixup to record the appropriate reloc. */ - /* FIXME: fr_targ.cgen is used pending deciding whether to - allow a target to add members to fragS. For more info - see the comment above fr_targ in as.h. */ - old_frag->fr_targ.cgen.insn = insn; - old_frag->fr_targ.cgen.opindex = fixups[relax_operand].opindex; - old_frag->fr_targ.cgen.opinfo = fixups[relax_operand].opinfo; + old_frag->fr_cgen.insn = insn; + old_frag->fr_cgen.opindex = fixups[relax_operand].opindex; + old_frag->fr_cgen.opinfo = fixups[relax_operand].opinfo; } else f = frag_more (byte_len); @@ -418,11 +450,11 @@ cgen_md_apply_fix3 (fixP, valueP, seg) if ((int) fixP->fx_r_type >= (int) BFD_RELOC_UNUSED) { int opindex = (int) fixP->fx_r_type - (int) BFD_RELOC_UNUSED; - const struct cgen_operand *operand = & CGEN_SYM (operand_table) [opindex]; + const CGEN_OPERAND *operand = & CGEN_SYM (operand_table) [opindex]; const char *errmsg; bfd_reloc_code_real_type reloc_type; - struct cgen_fields fields; - const struct cgen_insn *insn = (struct cgen_insn *) fixP->tc_fix_data.insn; + CGEN_FIELDS fields; + const CGEN_INSN *insn = (CGEN_INSN *) fixP->tc_fix_data.insn; /* If the reloc has been fully resolved finish the operand here. */ /* FIXME: This duplicates the capabilities of code in BFD. */ @@ -506,7 +538,7 @@ cgen_tc_gen_reloc (section, fixP) { arelent *reloc; - reloc = (arelent *) bfd_alloc_by_size_t (stdoutput, sizeof (arelent)); + reloc = (arelent *) bfd_alloc (stdoutput, sizeof (arelent)); reloc->howto = bfd_reloc_type_lookup (stdoutput, fixP->fx_r_type); if (reloc->howto == (reloc_howto_type *) NULL) -- 2.34.1