diff options
author | John David Anglin <danglin@gcc.gnu.org> | 2014-08-16 16:36:33 +0000 |
---|---|---|
committer | John David Anglin <danglin@gcc.gnu.org> | 2014-08-16 16:36:33 +0000 |
commit | 3ba07ad32081301b3e23716802ec26ba352dd5ac (patch) | |
tree | 232ae71258f3c9abc3172d69fabb376e0e1544a9 | |
parent | 5f05dc5550287bc09490f7aeeffbdad80288b5e5 (diff) | |
download | gcc-3ba07ad32081301b3e23716802ec26ba352dd5ac.zip gcc-3ba07ad32081301b3e23716802ec26ba352dd5ac.tar.gz gcc-3ba07ad32081301b3e23716802ec26ba352dd5ac.tar.bz2 |
re PR target/61641 (undefined label in jump_table_data)
PR target/61641
* config/pa/pa-protos.h (pa_output_addr_vec, pa_output_addr_diff_vec):
Declare.
* config/pa/pa.c (pa_reorg): Remove code to insert brtab marker insns.
(pa_output_addr_vec, pa_output_addr_diff_vec): New.
* config/pa/pa.h (ASM_OUTPUT_ADDR_VEC, ASM_OUTPUT_ADDR_DIFF_VEC):
Define.
* config/pa/pa.md (begin_brtab): Delete insn.
(end_brtab): Likewise.
From-SVN: r214064
-rw-r--r-- | gcc/ChangeLog | 12 | ||||
-rw-r--r-- | gcc/config/pa/pa-protos.h | 2 | ||||
-rw-r--r-- | gcc/config/pa/pa.c | 69 | ||||
-rw-r--r-- | gcc/config/pa/pa.h | 10 | ||||
-rw-r--r-- | gcc/config/pa/pa.md | 30 |
5 files changed, 67 insertions, 56 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 0d7dd91..081bd12 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,15 @@ +2014-08-16 John David Anglin <danglin@gcc.gnu.org> + + PR target/61641 + * config/pa/pa-protos.h (pa_output_addr_vec, pa_output_addr_diff_vec): + Declare. + * config/pa/pa.c (pa_reorg): Remove code to insert brtab marker insns. + (pa_output_addr_vec, pa_output_addr_diff_vec): New. + * config/pa/pa.h (ASM_OUTPUT_ADDR_VEC, ASM_OUTPUT_ADDR_DIFF_VEC): + Define. + * config/pa/pa.md (begin_brtab): Delete insn. + (end_brtab): Likewise. + 2014-08-16 Manuel López-Ibáñez <manu@gcc.gnu.org> * doc/cppopts.texi (ftrack-macro-expansion): Add missing @code. diff --git a/gcc/config/pa/pa-protos.h b/gcc/config/pa/pa-protos.h index e72abea..45031e2 100644 --- a/gcc/config/pa/pa-protos.h +++ b/gcc/config/pa/pa-protos.h @@ -49,6 +49,8 @@ extern const char *pa_output_mul_insn (int, rtx); extern const char *pa_output_div_insn (rtx *, int, rtx); extern const char *pa_output_mod_insn (int, rtx); extern const char *pa_singlemove_string (rtx *); +extern void pa_output_addr_vec (rtx, rtx); +extern void pa_output_addr_diff_vec (rtx, rtx); extern void pa_output_arg_descriptor (rtx); extern void pa_output_global_address (FILE *, rtx, int); extern void pa_print_operand (FILE *, rtx, int); diff --git a/gcc/config/pa/pa.c b/gcc/config/pa/pa.c index d52d52f..d47d5c8 100644 --- a/gcc/config/pa/pa.c +++ b/gcc/config/pa/pa.c @@ -8926,40 +8926,15 @@ pa_following_call (rtx insn) } /* We use this hook to perform a PA specific optimization which is difficult - to do in earlier passes. - - We surround the jump table itself with BEGIN_BRTAB and END_BRTAB - insns. Those insns mark where we should emit .begin_brtab and - .end_brtab directives when using GAS. This allows for better link - time optimizations. */ + to do in earlier passes. */ static void pa_reorg (void) { - rtx insn; - remove_useless_addtr_insns (1); if (pa_cpu < PROCESSOR_8000) pa_combine_instructions (); - - /* Still need brtab marker insns. FIXME: the presence of these - markers disables output of the branch table to readonly memory, - and any alignment directives that might be needed. Possibly, - the begin_brtab insn should be output before the label for the - table. This doesn't matter at the moment since the tables are - always output in the text section. */ - for (insn = get_insns (); insn; insn = NEXT_INSN (insn)) - { - /* Find an ADDR_VEC insn. */ - if (! JUMP_TABLE_DATA_P (insn)) - continue; - - /* Now generate markers for the beginning and end of the - branch table. */ - emit_insn_before (gen_begin_brtab (), insn); - emit_insn_after (gen_end_brtab (), insn); - } } /* The PA has a number of odd instructions which can perform multiple @@ -10554,4 +10529,46 @@ pa_legitimize_reload_address (rtx ad, enum machine_mode mode, return NULL_RTX; } +/* Output address vector. */ + +void +pa_output_addr_vec (rtx lab, rtx body) +{ + int idx, vlen = XVECLEN (body, 0); + + targetm.asm_out.internal_label (asm_out_file, "L", CODE_LABEL_NUMBER (lab)); + if (TARGET_GAS) + fputs ("\t.begin_brtab\n", asm_out_file); + for (idx = 0; idx < vlen; idx++) + { + ASM_OUTPUT_ADDR_VEC_ELT + (asm_out_file, CODE_LABEL_NUMBER (XEXP (XVECEXP (body, 0, idx), 0))); + } + if (TARGET_GAS) + fputs ("\t.end_brtab\n", asm_out_file); +} + +/* Output address difference vector. */ + +void +pa_output_addr_diff_vec (rtx lab, rtx body) +{ + rtx base = XEXP (XEXP (body, 0), 0); + int idx, vlen = XVECLEN (body, 1); + + targetm.asm_out.internal_label (asm_out_file, "L", CODE_LABEL_NUMBER (lab)); + if (TARGET_GAS) + fputs ("\t.begin_brtab\n", asm_out_file); + for (idx = 0; idx < vlen; idx++) + { + ASM_OUTPUT_ADDR_DIFF_ELT + (asm_out_file, + body, + CODE_LABEL_NUMBER (XEXP (XVECEXP (body, 1, idx), 0)), + CODE_LABEL_NUMBER (base)); + } + if (TARGET_GAS) + fputs ("\t.end_brtab\n", asm_out_file); +} + #include "gt-pa.h" diff --git a/gcc/config/pa/pa.h b/gcc/config/pa/pa.h index 7292d6a..9a1773f 100644 --- a/gcc/config/pa/pa.h +++ b/gcc/config/pa/pa.h @@ -1193,6 +1193,16 @@ do { \ #define ASM_OUTPUT_ADDR_DIFF_ELT(FILE, BODY, VALUE, REL) \ fprintf (FILE, "\t.word L$%04d-L$%04d\n", VALUE, REL) +/* This is how to output an absolute case-vector. */ + +#define ASM_OUTPUT_ADDR_VEC(LAB,BODY) \ + pa_output_addr_vec ((LAB),(BODY)) + +/* This is how to output a relative case-vector. */ + +#define ASM_OUTPUT_ADDR_DIFF_VEC(LAB,BODY) \ + pa_output_addr_diff_vec ((LAB),(BODY)) + /* This is how to output an assembler line that says to advance the location counter to a multiple of 2**LOG bytes. */ diff --git a/gcc/config/pa/pa.md b/gcc/config/pa/pa.md index e55d0b8..a9421ac 100644 --- a/gcc/config/pa/pa.md +++ b/gcc/config/pa/pa.md @@ -8508,36 +8508,6 @@ add,l %2,%3,%3\;bv,n %%r0(%3)" [(set_attr "type" "move") (set_attr "length" "4")]) -;; These are just placeholders so we know where branch tables -;; begin and end. -(define_insn "begin_brtab" - [(const_int 1)] - "" - "* -{ - /* Only GAS actually supports this pseudo-op. */ - if (TARGET_GAS) - return \".begin_brtab\"; - else - return \"\"; -}" - [(set_attr "type" "move") - (set_attr "length" "0")]) - -(define_insn "end_brtab" - [(const_int 2)] - "" - "* -{ - /* Only GAS actually supports this pseudo-op. */ - if (TARGET_GAS) - return \".end_brtab\"; - else - return \"\"; -}" - [(set_attr "type" "move") - (set_attr "length" "0")]) - ;;; EH does longjmp's from and within the data section. Thus, ;;; an interspace branch is required for the longjmp implementation. ;;; Registers r1 and r2 are used as scratch registers for the jump |