From: Alan Modra Date: Thu, 10 May 2001 11:32:52 +0000 (+0000) Subject: Fix more fallout from multi-pass relaxation patch. X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=606ab118baddd89493a504f6622c944562cc6bc5;p=binutils-gdb.git Fix more fallout from multi-pass relaxation patch. --- diff --git a/gas/ChangeLog b/gas/ChangeLog index 8d14cf27baa..272347e8cc9 100644 --- a/gas/ChangeLog +++ b/gas/ChangeLog @@ -1,3 +1,36 @@ +2001-05-10 Alan Modra + + * config/obj-vms.c (obj_crawl_symbol_chain): Don't take address of + symbol_next. + + * config/tc-fr30.c (md_estimate_size_before_relax): Return size of + current variable part of frag. + * config/tc-m32r.c (md_estimate_size_before_relax): Likewise. + * config/tc-openrisc.c (md_estimate_size_before_relax): Likewise. + * config/tc-m68hc11.c (RELAX_STATE): Define. + (RELAX_LENGTH): Define. + (md_estimate_size_before_relax): Handle non-relaxable cases + separately from relaxable cases for clarity, and return correct + size for multi-pass relaxation. + * config/tc-tahoe.c (RELAX_LENGTH): Correct. + (md_estimate_size_before_relax): As for tc-m68hc11.c. + (md_convert_frag): Remove "length_code". + * config/tc-vax.c (RELAX_STATE): Define. + (RELAX_LENGTH): Define. + (md_relax_table): Add missing entry. + (md_estimate_size_before_relax): As for tc-m68hc11.c. + (md_convert_frag): Remove "length_code". + * config/tc-ns32k.c (md_estimate_size_before_relax): Simplify and + don't bother setting fr_var. Return correct size for multi-pass + relaxation. + * config/tc-v850.c (md_estimate_size_before_relax): Rewrite. + (md_convert_frag): Don't bother clearing fr_var. + (md_pseudo_table): Correct initialization. + * config/tc-h8500.c (md_convert_frag): Don't bother clearing fr_var. + (md_estimate_size_before_relax): No need to set fr_var. + * config/tc-mcore.c (md_convert_frag): Don't bother clearing fr_var. + (md_estimate_size_before_relax): No need to set fr_var. + 2001-05-09 Richard Henderson * config/tc-ia64.c (generate_unwind_image): Align the fragment diff --git a/gas/config/obj-vms.c b/gas/config/obj-vms.c index 028e6b99246..3d1687569d5 100644 --- a/gas/config/obj-vms.c +++ b/gas/config/obj-vms.c @@ -552,7 +552,7 @@ obj_crawl_symbol_chain (headers) { symbolP->sy_number = symbol_number++; symbolP->sy_name_offset = 0; - symbolPP = &(symbol_next (symbolP)); + symbolPP = &symbolP->sy_next; } else { diff --git a/gas/config/tc-fr30.c b/gas/config/tc-fr30.c index d2cffc7b319..1acebb8928f 100644 --- a/gas/config/tc-fr30.c +++ b/gas/config/tc-fr30.c @@ -265,8 +265,6 @@ md_estimate_size_before_relax (fragP, segment) fragS * fragP; segT segment; { - int old_fr_fix = fragP->fr_fix; - /* The only thing we have to handle here are symbols outside of the current segment. They may be undefined or in a different segment in which case linker scripts may place them anywhere. @@ -275,6 +273,8 @@ md_estimate_size_before_relax (fragP, segment) if (S_GET_SEGMENT (fragP->fr_symbol) != segment) { + int old_fr_fix = fragP->fr_fix; + /* The symbol is undefined in this segment. Change the relaxation subtype to the max allowable and leave all further handling to md_convert_frag. */ @@ -297,6 +297,7 @@ md_estimate_size_before_relax (fragP, segment) /* Mark this fragment as finished. */ frag_wane (fragP); + return fragP->fr_fix - old_fr_fix; #else { const CGEN_INSN * insn; @@ -323,7 +324,8 @@ md_estimate_size_before_relax (fragP, segment) #endif } - return (fragP->fr_var + fragP->fr_fix - old_fr_fix); + /* Return the size of the variable part of the frag. */ + return md_relax_table[fragP->fr_subtype].rlx_length; } /* *fragP has been relaxed to its final size, and now needs to have diff --git a/gas/config/tc-h8500.c b/gas/config/tc-h8500.c index d0f6192e03a..a13c94268ed 100644 --- a/gas/config/tc-h8500.c +++ b/gas/config/tc-h8500.c @@ -1343,7 +1343,6 @@ md_convert_frag (headers, seg, fragP) R_H8500_PCREL16); fragP->fr_fix += disp_size + inst_size; - fragP->fr_var = 0; return; break; default: @@ -1359,7 +1358,6 @@ md_convert_frag (headers, seg, fragP) md_number_to_chars (buffer + inst_size, disp, disp_size); fragP->fr_fix += disp_size + inst_size; - fragP->fr_var = 0; } } @@ -1471,8 +1469,7 @@ md_estimate_size_before_relax (fragP, segment_type) break; } - fragP->fr_var = md_relax_table[fragP->fr_subtype].rlx_length; - return fragP->fr_var; + return md_relax_table[fragP->fr_subtype].rlx_length; } /* Put number into target byte order. */ diff --git a/gas/config/tc-m32r.c b/gas/config/tc-m32r.c index 51ef9fec77b..47378d48ee6 100644 --- a/gas/config/tc-m32r.c +++ b/gas/config/tc-m32r.c @@ -1441,8 +1441,6 @@ md_estimate_size_before_relax (fragP, segment) fragS *fragP; segT segment; { - int old_fr_fix = fragP->fr_fix; - /* The only thing we have to handle here are symbols outside of the current segment. They may be undefined or in a different segment in which case linker scripts may place them anywhere. @@ -1451,6 +1449,8 @@ md_estimate_size_before_relax (fragP, segment) if (S_GET_SEGMENT (fragP->fr_symbol) != segment) { + int old_fr_fix = fragP->fr_fix; + /* The symbol is undefined in this segment. Change the relaxation subtype to the max allowable and leave all further handling to md_convert_frag. */ @@ -1474,6 +1474,7 @@ md_estimate_size_before_relax (fragP, segment) /* Mark this fragment as finished. */ frag_wane (fragP); + return fragP->fr_fix - old_fr_fix; #else { const CGEN_INSN *insn; @@ -1500,7 +1501,7 @@ md_estimate_size_before_relax (fragP, segment) #endif } - return (fragP->fr_var + fragP->fr_fix - old_fr_fix); + return md_relax_table[fragP->fr_subtype].rlx_length; } /* *FRAGP has been relaxed to its final size, and now needs to have diff --git a/gas/config/tc-m68hc11.c b/gas/config/tc-m68hc11.c index d8e8545edfb..23ef33577f8 100644 --- a/gas/config/tc-m68hc11.c +++ b/gas/config/tc-m68hc11.c @@ -49,6 +49,8 @@ const char FLT_CHARS[] = "dD"; /* This macro has no side-effects. */ #define ENCODE_RELAX(what,length) (((what) << 2) + (length)) +#define RELAX_STATE(s) ((s) >> 2) +#define RELAX_LENGTH(s) ((s) & 3) #define IS_OPCODE(C1,C2) (((C1) & 0x0FF) == ((C2) & 0x0FF)) @@ -2563,145 +2565,153 @@ md_estimate_size_before_relax (fragP, segment) fragS *fragP; asection *segment; { - int old_fr_fix; - char *buffer_address = fragP->fr_fix + fragP->fr_literal; + if (RELAX_LENGTH (fragP->fr_subtype) == STATE_UNDF) + { + if (S_GET_SEGMENT (fragP->fr_symbol) != segment + || !relaxable_symbol (fragP->fr_symbol)) + { + /* Non-relaxable cases. */ + int old_fr_fix; + char *buffer_address; - old_fr_fix = fragP->fr_fix; + old_fr_fix = fragP->fr_fix; + buffer_address = fragP->fr_fix + fragP->fr_literal; - switch (fragP->fr_subtype) - { - case ENCODE_RELAX (STATE_PC_RELATIVE, STATE_UNDF): + switch (RELAX_STATE (fragP->fr_subtype)) + { + case STATE_PC_RELATIVE: + + /* This relax is only for bsr and bra. */ + assert (IS_OPCODE (fragP->fr_opcode[0], M6811_BSR) + || IS_OPCODE (fragP->fr_opcode[0], M6811_BRA) + || IS_OPCODE (fragP->fr_opcode[0], M6812_BSR)); + + if (flag_fixed_branchs) + as_bad_where (fragP->fr_file, fragP->fr_line, + _("bra or bsr with undefined symbol.")); + + /* The symbol is undefined or in a separate section. + Turn bra into a jmp and bsr into a jsr. The insn + becomes 3 bytes long (instead of 2). A fixup is + necessary for the unresolved symbol address. */ + fragP->fr_opcode[0] = convert_branch (fragP->fr_opcode[0]); + + fragP->fr_fix++; + fix_new (fragP, old_fr_fix - 1, 2, fragP->fr_symbol, + fragP->fr_offset, 0, BFD_RELOC_16); + break; - /* This relax is only for bsr and bra. */ - assert (IS_OPCODE (fragP->fr_opcode[0], M6811_BSR) - || IS_OPCODE (fragP->fr_opcode[0], M6811_BRA) - || IS_OPCODE (fragP->fr_opcode[0], M6812_BSR)); + case STATE_CONDITIONAL_BRANCH: + assert (current_architecture & cpu6811); - /* A relaxable case. */ - if (S_GET_SEGMENT (fragP->fr_symbol) == segment - && relaxable_symbol (fragP->fr_symbol)) - { - fragP->fr_subtype = ENCODE_RELAX (STATE_PC_RELATIVE, STATE_BYTE); - } - else - { - if (flag_fixed_branchs) - as_bad_where (fragP->fr_file, fragP->fr_line, - _("bra or bsr with undefined symbol.")); + fragP->fr_opcode[0] ^= 1; /* Reverse sense of branch. */ + fragP->fr_opcode[1] = 3; /* Skip next jmp insn (3 bytes). */ - /* The symbol is undefined or in a separate section. Turn bra into a - jmp and bsr into a jsr. The insn becomes 3 bytes long (instead of - 2). A fixup is necessary for the unresolved symbol address. */ + /* Don't use fr_opcode[2] because this may be + in a different frag. */ + buffer_address[0] = M6811_JMP; - fragP->fr_opcode[0] = convert_branch (fragP->fr_opcode[0]); + fragP->fr_fix++; + fix_new (fragP, fragP->fr_fix, 2, fragP->fr_symbol, + fragP->fr_offset, 0, BFD_RELOC_16); + fragP->fr_fix += 2; + break; - fragP->fr_fix++; - fix_new (fragP, old_fr_fix - 1, 2, fragP->fr_symbol, - fragP->fr_offset, 0, BFD_RELOC_16); - frag_wane (fragP); - } - break; + case STATE_INDEXED_OFFSET: + assert (current_architecture & cpu6812); - case ENCODE_RELAX (STATE_CONDITIONAL_BRANCH, STATE_UNDF): - assert (current_architecture & cpu6811); + /* Switch the indexed operation to 16-bit mode. */ + fragP->fr_opcode[0] = fragP->fr_opcode[0] << 3; + fragP->fr_opcode[0] |= 0xe2; + fragP->fr_fix++; + fix_new (fragP, fragP->fr_fix, 2, fragP->fr_symbol, + fragP->fr_offset, 0, BFD_RELOC_16); + fragP->fr_fix++; + break; - if (S_GET_SEGMENT (fragP->fr_symbol) == segment - && relaxable_symbol (fragP->fr_symbol)) - { - fragP->fr_subtype = ENCODE_RELAX (STATE_CONDITIONAL_BRANCH, - STATE_BYTE); - } - else - { - fragP->fr_opcode[0] ^= 1; /* Reverse sense of branch. */ - fragP->fr_opcode[1] = 3; /* Skip next jmp insn (3 bytes). */ + case STATE_XBCC_BRANCH: + assert (current_architecture & cpu6812); + + fragP->fr_opcode[0] ^= 0x20; /* Reverse sense of branch. */ + fragP->fr_opcode[1] = 3; /* Skip next jmp insn (3 bytes). */ - /* Don't use fr_opcode[2] because this may be - in a different frag. */ - buffer_address[0] = M6811_JMP; + /* Don't use fr_opcode[2] because this may be + in a different frag. */ + buffer_address[0] = M6812_JMP; + + fragP->fr_fix++; + fix_new (fragP, fragP->fr_fix, 2, fragP->fr_symbol, + fragP->fr_offset, 0, BFD_RELOC_16); + fragP->fr_fix += 2; + break; - fragP->fr_fix++; - fix_new (fragP, fragP->fr_fix, 2, fragP->fr_symbol, - fragP->fr_offset, 0, BFD_RELOC_16); - fragP->fr_fix += 2; + case STATE_CONDITIONAL_BRANCH_6812: + assert (current_architecture & cpu6812); + + /* Translate into a lbcc branch. */ + fragP->fr_opcode[1] = fragP->fr_opcode[0]; + fragP->fr_opcode[0] = M6811_OPCODE_PAGE2; + + fix_new (fragP, fragP->fr_fix, 2, fragP->fr_symbol, + fragP->fr_offset, 0, BFD_RELOC_16_PCREL); + fragP->fr_fix += 2; + break; + + default: + as_fatal (_("Subtype %d is not recognized."), fragP->fr_subtype); + } frag_wane (fragP); - } - break; - case ENCODE_RELAX (STATE_INDEXED_OFFSET, STATE_UNDF): - assert (current_architecture & cpu6812); + /* Return the growth in the fixed part of the frag. */ + return fragP->fr_fix - old_fr_fix; + } - if (S_GET_SEGMENT (fragP->fr_symbol) == segment - && relaxable_symbol (fragP->fr_symbol)) + /* Relaxable cases. */ + switch (RELAX_STATE (fragP->fr_subtype)) { + case STATE_PC_RELATIVE: + /* This relax is only for bsr and bra. */ + assert (IS_OPCODE (fragP->fr_opcode[0], M6811_BSR) + || IS_OPCODE (fragP->fr_opcode[0], M6811_BRA) + || IS_OPCODE (fragP->fr_opcode[0], M6812_BSR)); + + fragP->fr_subtype = ENCODE_RELAX (STATE_PC_RELATIVE, STATE_BYTE); + break; + + case STATE_CONDITIONAL_BRANCH: + assert (current_architecture & cpu6811); + + fragP->fr_subtype = ENCODE_RELAX (STATE_CONDITIONAL_BRANCH, + STATE_BYTE); + break; + + case STATE_INDEXED_OFFSET: + assert (current_architecture & cpu6812); + fragP->fr_subtype = ENCODE_RELAX (STATE_INDEXED_OFFSET, STATE_BITS5); - } - else - { - /* Switch the indexed operation to 16-bit mode. */ - fragP->fr_opcode[0] = fragP->fr_opcode[0] << 3; - fragP->fr_opcode[0] |= 0xe2; - fragP->fr_fix++; - fix_new (fragP, fragP->fr_fix, 2, fragP->fr_symbol, - fragP->fr_offset, 0, BFD_RELOC_16); - fragP->fr_fix++; - frag_wane (fragP); - } - break; + break; - case ENCODE_RELAX (STATE_XBCC_BRANCH, STATE_UNDF): - assert (current_architecture & cpu6812); + case STATE_XBCC_BRANCH: + assert (current_architecture & cpu6812); - if (S_GET_SEGMENT (fragP->fr_symbol) == segment - && relaxable_symbol (fragP->fr_symbol)) - { fragP->fr_subtype = ENCODE_RELAX (STATE_XBCC_BRANCH, STATE_BYTE); - } - else - { - fragP->fr_opcode[0] ^= 0x20; /* Reverse sense of branch. */ - fragP->fr_opcode[1] = 3; /* Skip next jmp insn (3 bytes). */ - - /* Don't use fr_opcode[2] because this may be - in a different frag. */ - buffer_address[0] = M6812_JMP; - - fragP->fr_fix++; - fix_new (fragP, fragP->fr_fix, 2, fragP->fr_symbol, - fragP->fr_offset, 0, BFD_RELOC_16); - fragP->fr_fix += 2; - frag_wane (fragP); - } - break; + break; - case ENCODE_RELAX (STATE_CONDITIONAL_BRANCH_6812, STATE_UNDF): - assert (current_architecture & cpu6812); + case STATE_CONDITIONAL_BRANCH_6812: + assert (current_architecture & cpu6812); - if (S_GET_SEGMENT (fragP->fr_symbol) == segment - && relaxable_symbol (fragP->fr_symbol)) - { fragP->fr_subtype = ENCODE_RELAX (STATE_CONDITIONAL_BRANCH_6812, STATE_BYTE); + break; } - else - { - /* Translate into a lbcc branch. */ - fragP->fr_opcode[1] = fragP->fr_opcode[0]; - fragP->fr_opcode[0] = M6811_OPCODE_PAGE2; - - fix_new (fragP, fragP->fr_fix, 2, fragP->fr_symbol, - fragP->fr_offset, 0, BFD_RELOC_16_PCREL); - fragP->fr_fix += 2; - frag_wane (fragP); - } - break; - - default: - as_fatal (_("Subtype %d is not recognized."), fragP->fr_subtype); } - return (fragP->fr_fix - old_fr_fix); + if (fragP->fr_subtype >= sizeof (md_relax_table) / sizeof (md_relax_table[0])) + as_fatal (_("Subtype %d is not recognized."), fragP->fr_subtype); + + /* Return the size of the variable part of the frag. */ + return md_relax_table[fragP->fr_subtype].rlx_length; } int diff --git a/gas/config/tc-mcore.c b/gas/config/tc-mcore.c index 15c9ce61f86..bb61d57fc22 100644 --- a/gas/config/tc-mcore.c +++ b/gas/config/tc-mcore.c @@ -1935,7 +1935,6 @@ md_convert_frag (abfd, sec, fragP) } fragP->fr_fix += 2; - fragP->fr_var = 0; } break; @@ -2026,8 +2025,6 @@ md_convert_frag (abfd, sec, fragP) else buffer[1] = 4; /* jmpi, ptr, and the 'tail pad' */ } - - fragP->fr_var = 0; } break; @@ -2082,8 +2079,6 @@ md_convert_frag (abfd, sec, fragP) fragP->fr_symbol, fragP->fr_offset, 0, BFD_RELOC_32); fragP->fr_fix += U32_LEN; } - - fragP->fr_var = 0; } break; @@ -2298,8 +2293,7 @@ md_estimate_size_before_relax (fragP, segment_type) break; } - fragP->fr_var = md_relax_table[fragP->fr_subtype].rlx_length; - return fragP->fr_var; + return md_relax_table[fragP->fr_subtype].rlx_length; } /* Put number into target byte order. */ diff --git a/gas/config/tc-ns32k.c b/gas/config/tc-ns32k.c index f66795c88c9..f8f01c6ffd3 100644 --- a/gas/config/tc-ns32k.c +++ b/gas/config/tc-ns32k.c @@ -2069,21 +2069,11 @@ md_estimate_size_before_relax (fragP, segment) register fragS *fragP; segT segment; { - int old_fix; - - old_fix = fragP->fr_fix; - - switch (fragP->fr_subtype) + if (fragP->fr_subtype == IND (BRANCH, UNDEF)) { - case IND (BRANCH, UNDEF): - if (S_GET_SEGMENT (fragP->fr_symbol) == segment) - { - /* The symbol has been assigned a value. */ - fragP->fr_subtype = IND (BRANCH, BYTE); - } - else + if (S_GET_SEGMENT (fragP->fr_symbol) != segment) { - /* We don't relax symbols defined in an other segment the + /* We don't relax symbols defined in another segment. The thing to do is to assume the object will occupy 4 bytes. */ fix_new_ns32k (fragP, (int) (fragP->fr_fix), @@ -2101,21 +2091,19 @@ md_estimate_size_before_relax (fragP, segment) fragP->fr_opcode[1] = 0xff; #endif frag_wane (fragP); - break; + return 4; } - /* Fall thru */ - case IND (BRANCH, BYTE): - case IND (BRANCH, WORD): - case IND (BRANCH, DOUBLE): - fragP->fr_var = md_relax_table[fragP->fr_subtype].rlx_length; - break; - - default: - break; + /* Relaxable case. Set up the initial guess for the variable + part of the frag. */ + fragP->fr_subtype = IND (BRANCH, BYTE); } - return fragP->fr_var + fragP->fr_fix - old_fix; + if (fragP->fr_subtype >= sizeof (md_relax_table) / sizeof (md_relax_table[0])) + abort (); + + /* Return the size of the variable part of the frag. */ + return md_relax_table[fragP->fr_subtype].rlx_length; } int md_short_jump_size = 3; diff --git a/gas/config/tc-openrisc.c b/gas/config/tc-openrisc.c index 2907cd48974..1aae4b4bf82 100644 --- a/gas/config/tc-openrisc.c +++ b/gas/config/tc-openrisc.c @@ -277,8 +277,6 @@ md_estimate_size_before_relax (fragP, segment) fragS * fragP; segT segment; { - int old_fr_fix = fragP->fr_fix; - /* The only thing we have to handle here are symbols outside of the current segment. They may be undefined or in a different segment in which case linker scripts may place them anywhere. @@ -316,7 +314,7 @@ md_estimate_size_before_relax (fragP, segment) } } - return (fragP->fr_var + fragP->fr_fix - old_fr_fix); + return md_relax_table[fragP->fr_subtype].rlx_length; } /* *fragP has been relaxed to its final size, and now needs to have diff --git a/gas/config/tc-tahoe.c b/gas/config/tc-tahoe.c index a25e767b1eb..f4f781a5d5d 100644 --- a/gas/config/tc-tahoe.c +++ b/gas/config/tc-tahoe.c @@ -245,8 +245,8 @@ pc_rel_disp? That sort of thing.) */ #define C(a,b) ENCODE_RELAX(a,b) /* This macro has no side-effects. */ #define ENCODE_RELAX(what,length) (((what) << 2) + (length)) -#define RELAX_STATE(what) ((what) >> 2) -#define RELAX_LENGTH(length) ((length) && 3) +#define RELAX_STATE(s) ((s) >> 2) +#define RELAX_LENGTH(s) ((s) & 3) #define STATE_ALWAYS_BRANCH (1) #define STATE_CONDITIONAL_BRANCH (2) @@ -604,136 +604,113 @@ md_create_long_jump (ptr, from_addr, to_addr, frag, to_symbol) md_number_to_chars (ptr, offset, 4); } -/* - * md_estimate_size_before_relax() - * - * Called just before relax(). - * Any symbol that is now undefined will not become defined, so we assumed - * that it will be resolved by the linker. - * Return the correct fr_subtype in the frag, for relax() - * Return the initial "guess for fr_var" to caller. (How big I think this - * will be.) - * The guess for fr_var is ACTUALLY the growth beyond fr_fix. - * Whatever we do to grow fr_fix or fr_var contributes to our returned value. - * Although it may not be explicit in the frag, pretend fr_var starts with a - * 0 value. - */ +/* md_estimate_size_before_relax(), called just before relax(). + Any symbol that is now undefined will not become defined. + Return the correct fr_subtype in the frag and the growth beyond + fr_fix. */ int md_estimate_size_before_relax (fragP, segment_type) register fragS *fragP; segT segment_type; /* N_DATA or N_TEXT. */ { - register char *p; - register int old_fr_fix; - /* int pc_rel; FIXME: remove this */ - - old_fr_fix = fragP->fr_fix; - switch (fragP->fr_subtype) + if (RELAX_LENGTH (fragP->fr_subtype) == STATE_UNDF) { - case ENCODE_RELAX (STATE_PC_RELATIVE, STATE_UNDF): - if (S_GET_SEGMENT (fragP->fr_symbol) == segment_type) + if (S_GET_SEGMENT (fragP->fr_symbol) != segment) { - /* The symbol was in the same segment as the opcode, and it's - a real pc_rel case so it's a relaxable case. */ - fragP->fr_subtype = ENCODE_RELAX (STATE_PC_RELATIVE, STATE_BYTE); - } - else - { - /* This case is still undefined, so asume it's a long word for the - linker to fix. */ - p = fragP->fr_literal + old_fr_fix; - *p |= TAHOE_PC_OR_LONG; - /* We now know how big it will be, one long word. */ - fragP->fr_fix += 1 + 4; - fix_new (fragP, old_fr_fix + 1, fragP->fr_symbol, - fragP->fr_offset, FX_PCREL32, NULL); - frag_wane (fragP); - } - break; + /* Non-relaxable cases. */ + char *p; + int old_fr_fix; - case ENCODE_RELAX (STATE_CONDITIONAL_BRANCH, STATE_UNDF): - if (S_GET_SEGMENT (fragP->fr_symbol) == segment_type) - { - fragP->fr_subtype = ENCODE_RELAX (STATE_CONDITIONAL_BRANCH, STATE_BYTE); - } - else - { + old_fr_fix = fragP->fr_fix; p = fragP->fr_literal + old_fr_fix; - *fragP->fr_opcode ^= 0x10; /* Reverse sense of branch. */ - *p++ = 6; - *p++ = TAHOE_JMP; - *p++ = TAHOE_PC_REL_LONG; - fragP->fr_fix += 1 + 1 + 1 + 4; - fix_new (fragP, old_fr_fix + 3, fragP->fr_symbol, - fragP->fr_offset, FX_PCREL32, NULL); + switch (RELAX_STATE (fragP->fr_subtype)) + { + case STATE_PC_RELATIVE: + *p |= TAHOE_PC_OR_LONG; + /* We now know how big it will be, one long word. */ + fragP->fr_fix += 1 + 4; + fix_new (fragP, old_fr_fix + 1, fragP->fr_symbol, + fragP->fr_offset, FX_PCREL32, NULL); + break; + + case STATE_CONDITIONAL_BRANCH: + *fragP->fr_opcode ^= 0x10; /* Reverse sense of branch. */ + *p++ = 6; + *p++ = TAHOE_JMP; + *p++ = TAHOE_PC_REL_LONG; + fragP->fr_fix += 1 + 1 + 1 + 4; + fix_new (fragP, old_fr_fix + 3, fragP->fr_symbol, + fragP->fr_offset, FX_PCREL32, NULL); + break; + + case STATE_BIG_REV_BRANCH: + *fragP->fr_opcode ^= 0x10; /* Reverse sense of branch. */ + *p++ = 0; + *p++ = 6; + *p++ = TAHOE_JMP; + *p++ = TAHOE_PC_REL_LONG; + fragP->fr_fix += 2 + 2 + 4; + fix_new (fragP, old_fr_fix + 4, fragP->fr_symbol, + fragP->fr_offset, FX_PCREL32, NULL); + break; + + case STATE_BIG_NON_REV_BRANCH: + *p++ = 2; + *p++ = 0; + *p++ = TAHOE_BRB; + *p++ = 6; + *p++ = TAHOE_JMP; + *p++ = TAHOE_PC_REL_LONG; + fragP->fr_fix += 2 + 2 + 2 + 4; + fix_new (fragP, old_fr_fix + 6, fragP->fr_symbol, + fragP->fr_offset, FX_PCREL32, NULL); + break; + + case STATE_ALWAYS_BRANCH: + *fragP->fr_opcode = TAHOE_JMP; + *p++ = TAHOE_PC_REL_LONG; + fragP->fr_fix += 1 + 4; + fix_new (fragP, old_fr_fix + 1, fragP->fr_symbol, + fragP->fr_offset, FX_PCREL32, NULL); + break; + + default: + abort (); + } frag_wane (fragP); - } - break; - case ENCODE_RELAX (STATE_BIG_REV_BRANCH, STATE_UNDF): - if (S_GET_SEGMENT (fragP->fr_symbol) == segment_type) - { - fragP->fr_subtype = - ENCODE_RELAX (STATE_BIG_REV_BRANCH, STATE_WORD); + /* Return the growth in the fixed part of the frag. */ + return fragP->fr_fix - old_fr_fix; } - else - { - p = fragP->fr_literal + old_fr_fix; - *fragP->fr_opcode ^= 0x10; /* Reverse sense of branch. */ - *p++ = 0; - *p++ = 6; - *p++ = TAHOE_JMP; - *p++ = TAHOE_PC_REL_LONG; - fragP->fr_fix += 2 + 2 + 4; - fix_new (fragP, old_fr_fix + 4, fragP->fr_symbol, - fragP->fr_offset, FX_PCREL32, NULL); - frag_wane (fragP); - } - break; - case ENCODE_RELAX (STATE_BIG_NON_REV_BRANCH, STATE_UNDF): - if (S_GET_SEGMENT (fragP->fr_symbol) == segment_type) + /* Relaxable cases. Set up the initial guess for the variable + part of the frag. */ + switch (RELAX_STATE (fragP->fr_subtype)) { + case STATE_PC_RELATIVE: + fragP->fr_subtype = ENCODE_RELAX (STATE_PC_RELATIVE, STATE_BYTE); + break; + case STATE_CONDITIONAL_BRANCH: + fragP->fr_subtype = ENCODE_RELAX (STATE_CONDITIONAL_BRANCH, STATE_BYTE); + break; + case STATE_BIG_REV_BRANCH: + fragP->fr_subtype = ENCODE_RELAX (STATE_BIG_REV_BRANCH, STATE_WORD); + break; + case STATE_BIG_NON_REV_BRANCH: fragP->fr_subtype = ENCODE_RELAX (STATE_BIG_NON_REV_BRANCH, STATE_WORD); - } - else - { - p = fragP->fr_literal + old_fr_fix; - *p++ = 2; - *p++ = 0; - *p++ = TAHOE_BRB; - *p++ = 6; - *p++ = TAHOE_JMP; - *p++ = TAHOE_PC_REL_LONG; - fragP->fr_fix += 2 + 2 + 2 + 4; - fix_new (fragP, old_fr_fix + 6, fragP->fr_symbol, - fragP->fr_offset, FX_PCREL32, NULL); - frag_wane (fragP); - } - break; - - case ENCODE_RELAX (STATE_ALWAYS_BRANCH, STATE_UNDF): - if (S_GET_SEGMENT (fragP->fr_symbol) == segment_type) - { + break; + case STATE_ALWAYS_BRANCH: fragP->fr_subtype = ENCODE_RELAX (STATE_ALWAYS_BRANCH, STATE_BYTE); + break; } - else - { - p = fragP->fr_literal + old_fr_fix; - *fragP->fr_opcode = TAHOE_JMP; - *p++ = TAHOE_PC_REL_LONG; - fragP->fr_fix += 1 + 4; - fix_new (fragP, old_fr_fix + 1, fragP->fr_symbol, - fragP->fr_offset, FX_PCREL32, NULL); - frag_wane (fragP); - } - break; - - default: - break; } - return (fragP->fr_var + fragP->fr_fix - old_fr_fix); -} /* md_estimate_size_before_relax() */ + + if (fragP->fr_subtype >= sizeof (md_relax_table) / sizeof (md_relax_table[0])) + abort (); + + /* Return the size of the variable part of the frag. */ + return md_relax_table[fragP->fr_subtype].rlx_length; +} /* * md_convert_frag(); @@ -754,7 +731,6 @@ md_convert_frag (headers, seg, fragP) { register char *addressP; /* -> _var to change. */ register char *opcodeP; /* -> opcode char(s) to change. */ - register short int length_code; /* 2=long 1=word 0=byte */ register short int extension = 0; /* Size of relaxed address. Added to fr_fix: incl. ALL var chars. */ register symbolS *symbolP; @@ -765,8 +741,6 @@ md_convert_frag (headers, seg, fragP) /* Where, in file space, does addr point? */ know (fragP->fr_type == rs_machine_dependent); - length_code = RELAX_LENGTH (fragP->fr_subtype); - know (length_code >= 0 && length_code < 3); where = fragP->fr_fix; addressP = fragP->fr_literal + where; opcodeP = fragP->fr_opcode; diff --git a/gas/config/tc-v850.c b/gas/config/tc-v850.c index 1f157d7c303..89f4b987899 100644 --- a/gas/config/tc-v850.c +++ b/gas/config/tc-v850.c @@ -604,8 +604,8 @@ const pseudo_typeS md_pseudo_table[] = { {"call_table_text", v850_call_table_text, 0}, {"v850e", set_machine, bfd_mach_v850e}, {"v850ea", set_machine, bfd_mach_v850ea}, - {"file", dwarf2_directive_file }, - {"loc", dwarf2_directive_loc }, + {"file", dwarf2_directive_file, 0}, + {"loc", dwarf2_directive_loc, 0}, { NULL, NULL, 0} }; @@ -1321,7 +1321,6 @@ md_convert_frag (abfd, sec, fragP) { fix_new (fragP, fragP->fr_fix, 2, fragP->fr_symbol, fragP->fr_offset, 1, BFD_RELOC_UNUSED + (int)fragP->fr_opcode); - fragP->fr_var = 0; fragP->fr_fix += 2; } /* Out of range conditional branch. Emit a branch around a jump. */ @@ -1345,7 +1344,6 @@ md_convert_frag (abfd, sec, fragP) fix_new (fragP, fragP->fr_fix + 2, 4, fragP->fr_symbol, fragP->fr_offset, 1, BFD_RELOC_UNUSED + (int) fragP->fr_opcode + 1); - fragP->fr_var = 0; fragP->fr_fix += 6; } /* Out of range unconditional branch. Emit a jump. */ @@ -1355,7 +1353,6 @@ md_convert_frag (abfd, sec, fragP) fix_new (fragP, fragP->fr_fix, 4, fragP->fr_symbol, fragP->fr_offset, 1, BFD_RELOC_UNUSED + (int) fragP->fr_opcode + 1); - fragP->fr_var = 0; fragP->fr_fix += 4; } else @@ -2315,20 +2312,17 @@ tc_gen_reloc (seg, fixp) return reloc; } -/* Assume everything will fit in two bytes, then expand as necessary. */ +/* Return current size of variable part of frag. */ int md_estimate_size_before_relax (fragp, seg) fragS *fragp; asection *seg ATTRIBUTE_UNUSED; { - if (fragp->fr_subtype == 0) - fragp->fr_var = 4; - else if (fragp->fr_subtype == 2) - fragp->fr_var = 2; - else + if (fragp->fr_subtype >= sizeof (md_relax_table) / sizeof (md_relax_table[0])) abort (); - return 2; + + return md_relax_table[fragp->fr_subtype].rlx_length; } long diff --git a/gas/config/tc-vax.c b/gas/config/tc-vax.c index 275bff9dacd..bf6558ced6c 100644 --- a/gas/config/tc-vax.c +++ b/gas/config/tc-vax.c @@ -181,6 +181,8 @@ int flag_no_hash_mixed_case; /* -h NUM */ #define C(a,b) ENCODE_RELAX(a,b) /* This macro has no side-effects. */ #define ENCODE_RELAX(what,length) (((what) << 2) + (length)) +#define RELAX_STATE(s) ((s) >> 2) +#define RELAX_LENGTH(s) ((s) & 3) const relax_typeS md_relax_table[] = { @@ -188,25 +190,31 @@ const relax_typeS md_relax_table[] = {1, 1, 0, 0}, /* unused 0,1 */ {1, 1, 0, 0}, /* unused 0,2 */ {1, 1, 0, 0}, /* unused 0,3 */ + {BF + 1, BB + 1, 2, C (1, 1)},/* B^"foo" 1,0 */ {WF + 1, WB + 1, 3, C (1, 2)},/* W^"foo" 1,1 */ {0, 0, 5, 0}, /* L^"foo" 1,2 */ {1, 1, 0, 0}, /* unused 1,3 */ + {BF, BB, 1, C (2, 1)}, /* b B^"foo" 2,0 */ {WF + 2, WB + 2, 4, C (2, 2)},/* br.+? brw X 2,1 */ {0, 0, 7, 0}, /* br.+? jmp X 2,2 */ {1, 1, 0, 0}, /* unused 2,3 */ + {BF, BB, 1, C (3, 1)}, /* brb B^foo 3,0 */ {WF, WB, 2, C (3, 2)}, /* brw W^foo 3,1 */ {0, 0, 5, 0}, /* Jmp L^foo 3,2 */ {1, 1, 0, 0}, /* unused 3,3 */ + {1, 1, 0, 0}, /* unused 4,0 */ {WF, WB, 2, C (4, 2)}, /* acb_ ^Wfoo 4,1 */ {0, 0, 10, 0}, /* acb_,br,jmp L^foo4,2 */ {1, 1, 0, 0}, /* unused 4,3 */ + {BF, BB, 1, C (5, 1)}, /* Xob___,,foo 5,0 */ {WF + 4, WB + 4, 6, C (5, 2)},/* Xob.+2,brb.+3,brw5,1 */ {0, 0, 9, 0}, /* Xob.+2,brb.+6,jmp5,2 */ + {1, 1, 0, 0}, /* unused 5,3 */ }; #undef C @@ -1140,127 +1148,112 @@ md_assemble (instruction_string) } /* for(operandP) */ } /* vax_assemble() */ -/* - * md_estimate_size_before_relax() - * - * Called just before relax(). - * Any symbol that is now undefined will not become defined. - * Return the correct fr_subtype in the frag. - * Return the initial "guess for fr_var" to caller. - * The guess for fr_var is ACTUALLY the growth beyond fr_fix. - * Whatever we do to grow fr_fix or fr_var contributes to our returned value. - * Although it may not be explicit in the frag, pretend fr_var starts with a - * 0 value. - */ +/* md_estimate_size_before_relax(), called just before relax(). + Any symbol that is now undefined will not become defined. + Return the correct fr_subtype in the frag and the growth beyond + fr_fix. */ int md_estimate_size_before_relax (fragP, segment) fragS *fragP; segT segment; { - char *p; - int old_fr_fix; - - old_fr_fix = fragP->fr_fix; - switch (fragP->fr_subtype) + if (RELAX_LENGTH (fragP->fr_subtype) == STATE_UNDF) { - case ENCODE_RELAX (STATE_PC_RELATIVE, STATE_UNDF): - if (S_GET_SEGMENT (fragP->fr_symbol) == segment) - { /* A relaxable case. */ - fragP->fr_subtype = ENCODE_RELAX (STATE_PC_RELATIVE, STATE_BYTE); - } - else + if (S_GET_SEGMENT (fragP->fr_symbol) != segment) { - p = fragP->fr_literal + old_fr_fix; - p[0] |= VAX_PC_RELATIVE_MODE; /* Preserve @ bit. */ - fragP->fr_fix += 1 + 4; - fix_new (fragP, old_fr_fix + 1, 4, fragP->fr_symbol, - fragP->fr_offset, 1, NO_RELOC); - frag_wane (fragP); - } - break; + /* Non-relaxable cases. */ + char *p; + int old_fr_fix; - case ENCODE_RELAX (STATE_CONDITIONAL_BRANCH, STATE_UNDF): - if (S_GET_SEGMENT (fragP->fr_symbol) == segment) - { - fragP->fr_subtype = ENCODE_RELAX (STATE_CONDITIONAL_BRANCH, STATE_BYTE); - } - else - { + old_fr_fix = fragP->fr_fix; p = fragP->fr_literal + old_fr_fix; - *fragP->fr_opcode ^= 1; /* Reverse sense of branch. */ - p[0] = 6; - p[1] = VAX_JMP; - p[2] = VAX_PC_RELATIVE_MODE; /* ...(PC) */ - fragP->fr_fix += 1 + 1 + 1 + 4; - fix_new (fragP, old_fr_fix + 3, 4, fragP->fr_symbol, - fragP->fr_offset, 1, NO_RELOC); - frag_wane (fragP); - } - break; + switch (RELAX_STATE (fragP->fr_subtype)) + { + case STATE_PC_RELATIVE: + p[0] |= VAX_PC_RELATIVE_MODE; /* Preserve @ bit. */ + fragP->fr_fix += 1 + 4; + fix_new (fragP, old_fr_fix + 1, 4, fragP->fr_symbol, + fragP->fr_offset, 1, NO_RELOC); + break; - case ENCODE_RELAX (STATE_COMPLEX_BRANCH, STATE_UNDF): - if (S_GET_SEGMENT (fragP->fr_symbol) == segment) - { - fragP->fr_subtype = ENCODE_RELAX (STATE_COMPLEX_BRANCH, STATE_WORD); - } - else - { - p = fragP->fr_literal + old_fr_fix; - p[0] = 2; - p[1] = 0; - p[2] = VAX_BRB; - p[3] = 6; - p[4] = VAX_JMP; - p[5] = VAX_PC_RELATIVE_MODE; /* ...(pc) */ - fragP->fr_fix += 2 + 2 + 1 + 1 + 4; - fix_new (fragP, old_fr_fix + 6, 4, fragP->fr_symbol, - fragP->fr_offset, 1, NO_RELOC); - frag_wane (fragP); - } - break; + case STATE_CONDITIONAL_BRANCH: + *fragP->fr_opcode ^= 1; /* Reverse sense of branch. */ + p[0] = 6; + p[1] = VAX_JMP; + p[2] = VAX_PC_RELATIVE_MODE; /* ...(PC) */ + fragP->fr_fix += 1 + 1 + 1 + 4; + fix_new (fragP, old_fr_fix + 3, 4, fragP->fr_symbol, + fragP->fr_offset, 1, NO_RELOC); + break; - case ENCODE_RELAX (STATE_COMPLEX_HOP, STATE_UNDF): - if (S_GET_SEGMENT (fragP->fr_symbol) == segment) - { - fragP->fr_subtype = ENCODE_RELAX (STATE_COMPLEX_HOP, STATE_BYTE); - } - else - { - p = fragP->fr_literal + old_fr_fix; - p[0] = 2; - p[1] = VAX_BRB; - p[2] = 6; - p[3] = VAX_JMP; - p[4] = VAX_PC_RELATIVE_MODE; /* ...(pc) */ - fragP->fr_fix += 1 + 2 + 1 + 1 + 4; - fix_new (fragP, old_fr_fix + 5, 4, fragP->fr_symbol, - fragP->fr_offset, 1, NO_RELOC); + case STATE_COMPLEX_BRANCH: + p[0] = 2; + p[1] = 0; + p[2] = VAX_BRB; + p[3] = 6; + p[4] = VAX_JMP; + p[5] = VAX_PC_RELATIVE_MODE; /* ...(pc) */ + fragP->fr_fix += 2 + 2 + 1 + 1 + 4; + fix_new (fragP, old_fr_fix + 6, 4, fragP->fr_symbol, + fragP->fr_offset, 1, NO_RELOC); + break; + + case STATE_COMPLEX_HOP: + p[0] = 2; + p[1] = VAX_BRB; + p[2] = 6; + p[3] = VAX_JMP; + p[4] = VAX_PC_RELATIVE_MODE; /* ...(pc) */ + fragP->fr_fix += 1 + 2 + 1 + 1 + 4; + fix_new (fragP, old_fr_fix + 5, 4, fragP->fr_symbol, + fragP->fr_offset, 1, NO_RELOC); + break; + + case STATE_ALWAYS_BRANCH: + *fragP->fr_opcode += VAX_WIDEN_LONG; + p[0] = VAX_PC_RELATIVE_MODE; /* ...(PC) */ + fragP->fr_fix += 1 + 4; + fix_new (fragP, old_fr_fix + 1, 4, fragP->fr_symbol, + fragP->fr_offset, 1, NO_RELOC); + break; + + default: + abort (); + } frag_wane (fragP); + + /* Return the growth in the fixed part of the frag. */ + return fragP->fr_fix - old_fr_fix; } - break; - case ENCODE_RELAX (STATE_ALWAYS_BRANCH, STATE_UNDF): - if (S_GET_SEGMENT (fragP->fr_symbol) == segment) + /* Relaxable cases. Set up the initial guess for the variable + part of the frag. */ + switch (RELAX_STATE (fragP->fr_subtype)) { + case STATE_PC_RELATIVE: + fragP->fr_subtype = ENCODE_RELAX (STATE_PC_RELATIVE, STATE_BYTE); + break; + case STATE_CONDITIONAL_BRANCH: + fragP->fr_subtype = ENCODE_RELAX (STATE_CONDITIONAL_BRANCH, STATE_BYTE); + break; + case STATE_COMPLEX_BRANCH: + fragP->fr_subtype = ENCODE_RELAX (STATE_COMPLEX_BRANCH, STATE_WORD); + break; + case STATE_COMPLEX_HOP: + fragP->fr_subtype = ENCODE_RELAX (STATE_COMPLEX_HOP, STATE_BYTE); + break; + case STATE_ALWAYS_BRANCH: fragP->fr_subtype = ENCODE_RELAX (STATE_ALWAYS_BRANCH, STATE_BYTE); + break; } - else - { - p = fragP->fr_literal + old_fr_fix; - *fragP->fr_opcode += VAX_WIDEN_LONG; - p[0] = VAX_PC_RELATIVE_MODE; /* ...(PC) */ - fragP->fr_fix += 1 + 4; - fix_new (fragP, old_fr_fix + 1, 4, fragP->fr_symbol, - fragP->fr_offset, 1, NO_RELOC); - frag_wane (fragP); - } - break; - - default: - break; } - return (fragP->fr_var + fragP->fr_fix - old_fr_fix); -} /* md_estimate_size_before_relax() */ + + if (fragP->fr_subtype >= sizeof (md_relax_table) / sizeof (md_relax_table[0])) + abort (); + + /* Return the size of the variable part of the frag. */ + return md_relax_table[fragP->fr_subtype].rlx_length; +} /* * md_convert_frag(); @@ -1281,7 +1274,6 @@ md_convert_frag (headers, seg, fragP) { char *addressP; /* -> _var to change. */ char *opcodeP; /* -> opcode char(s) to change. */ - short int length_code; /* 2=long 1=word 0=byte */ short int extension = 0; /* Size of relaxed address. */ /* Added to fr_fix: incl. ALL var chars. */ symbolS *symbolP; @@ -1292,8 +1284,6 @@ md_convert_frag (headers, seg, fragP) /* Where, in file space, does addr point? */ know (fragP->fr_type == rs_machine_dependent); - length_code = fragP->fr_subtype & 3; /* depends on ENCODE_RELAX() */ - know (length_code >= 0 && length_code < 3); where = fragP->fr_fix; addressP = fragP->fr_literal + where; opcodeP = fragP->fr_opcode;