diff options
author | ebotcazou <ebotcazou@138bc75d-0d04-0410-961f-82ee72b054a4> | 2005-05-25 07:04:04 +0000 |
---|---|---|
committer | ebotcazou <ebotcazou@138bc75d-0d04-0410-961f-82ee72b054a4> | 2005-05-25 07:04:04 +0000 |
commit | 76d4bacb4f5fd50773dce38c67fd4b889bb3f71c (patch) | |
tree | 484e1f45bb64046a2af02ae5b5edc1eb51ecbfca /gcc | |
parent | 9b2d6d13808845e60fdd0047dcf2b626c641f75d (diff) | |
download | gcc-76d4bacb4f5fd50773dce38c67fd4b889bb3f71c.tar.gz |
PR target/21412
* config/sparc/sparc.h (SPARC_SYMBOL_REF_TLS_P): New macro
* config/sparc/sparc-protos.h (tls_symbolic_operand): Delete.
(sparc_tls_referenced_p): New prototype.
* config/sparc/sparc.c (tls_symbolic_operand): Delete.
(sparc_expand_move): Look for TLS addresses with constant offsets.
(legitimate_constant_p): Use SPARC_SYMBOL_REF_TLS_P instead of
tls_symbolic_operand.
(legitimate_pic_operand_p): Likewise.
(legitimate_address_p): Likewise.
(legitimize_address): Likewise.
(sparc_tls_symbol_ref_1): New function.
(sparc_tls_referenced_p): New function.
* config/sparc/predicates.md (tgd_symbolic_operand): Use
SYMBOL_REF_TLS_MODEL instead of tls_symbolic_operand.
(tld_symbolic_operand): Likewise.
(tie_symbolic_operand): Likewise.
(tle_symbolic_operand): Likewise.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@100137 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/ChangeLog | 21 | ||||
-rw-r--r-- | gcc/config/sparc/predicates.md | 8 | ||||
-rw-r--r-- | gcc/config/sparc/sparc-protos.h | 2 | ||||
-rw-r--r-- | gcc/config/sparc/sparc.c | 70 | ||||
-rw-r--r-- | gcc/config/sparc/sparc.h | 3 |
5 files changed, 79 insertions, 25 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 01d57e2da3d..d6aa061f637 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,24 @@ +2005-05-25 Eric Botcazou <ebotcazou@libertysurf.fr> + + PR target/21412 + * config/sparc/sparc.h (SPARC_SYMBOL_REF_TLS_P): New macro + * config/sparc/sparc-protos.h (tls_symbolic_operand): Delete. + (sparc_tls_referenced_p): New prototype. + * config/sparc/sparc.c (tls_symbolic_operand): Delete. + (sparc_expand_move): Look for TLS addresses with constant offsets. + (legitimate_constant_p): Use SPARC_SYMBOL_REF_TLS_P instead of + tls_symbolic_operand. + (legitimate_pic_operand_p): Likewise. + (legitimate_address_p): Likewise. + (legitimize_address): Likewise. + (sparc_tls_symbol_ref_1): New function. + (sparc_tls_referenced_p): New function. + * config/sparc/predicates.md (tgd_symbolic_operand): Use + SYMBOL_REF_TLS_MODEL instead of tls_symbolic_operand. + (tld_symbolic_operand): Likewise. + (tie_symbolic_operand): Likewise. + (tle_symbolic_operand): Likewise. + 2005-05-24 DJ Delorie <dj@redhat.com> * common.opt (-Wattributes): New. Default true. diff --git a/gcc/config/sparc/predicates.md b/gcc/config/sparc/predicates.md index 752286cb184..a0e9b04fad3 100644 --- a/gcc/config/sparc/predicates.md +++ b/gcc/config/sparc/predicates.md @@ -120,22 +120,22 @@ ;; Return true if OP is a symbolic operand for the TLS Global Dynamic model. (define_predicate "tgd_symbolic_operand" (and (match_code "symbol_ref") - (match_test "tls_symbolic_operand (op) == TLS_MODEL_GLOBAL_DYNAMIC"))) + (match_test "SYMBOL_REF_TLS_MODEL (op) == TLS_MODEL_GLOBAL_DYNAMIC"))) ;; Return true if OP is a symbolic operand for the TLS Local Dynamic model. (define_predicate "tld_symbolic_operand" (and (match_code "symbol_ref") - (match_test "tls_symbolic_operand (op) == TLS_MODEL_LOCAL_DYNAMIC"))) + (match_test "SYMBOL_REF_TLS_MODEL (op) == TLS_MODEL_LOCAL_DYNAMIC"))) ;; Return true if OP is a symbolic operand for the TLS Initial Exec model. (define_predicate "tie_symbolic_operand" (and (match_code "symbol_ref") - (match_test "tls_symbolic_operand (op) == TLS_MODEL_INITIAL_EXEC"))) + (match_test "SYMBOL_REF_TLS_MODEL (op) == TLS_MODEL_INITIAL_EXEC"))) ;; Return true if OP is a symbolic operand for the TLS Local Exec model. (define_predicate "tle_symbolic_operand" (and (match_code "symbol_ref") - (match_test "tls_symbolic_operand (op) == TLS_MODEL_LOCAL_EXEC"))) + (match_test "SYMBOL_REF_TLS_MODEL (op) == TLS_MODEL_LOCAL_EXEC"))) ;; Return true if the operand is an argument used in generating PIC references ;; in either the medium/low or embedded medium/anywhere code models on V9. diff --git a/gcc/config/sparc/sparc-protos.h b/gcc/config/sparc/sparc-protos.h index a29bd691509..9c1e3721b72 100644 --- a/gcc/config/sparc/sparc-protos.h +++ b/gcc/config/sparc/sparc-protos.h @@ -94,7 +94,6 @@ extern int arith_4096_operand (rtx, enum machine_mode); extern int zero_operand (rtx, enum machine_mode); extern int fp_zero_operand (rtx, enum machine_mode); extern int reg_or_0_operand (rtx, enum machine_mode); -extern int tls_symbolic_operand (rtx); extern int empty_delay_slot (rtx); extern int eligible_for_return_delay (rtx); extern int eligible_for_sibcall_delay (rtx); @@ -103,6 +102,7 @@ extern int emit_move_sequence (rtx, enum machine_mode); extern int fp_sethi_p (rtx); extern int fp_mov_p (rtx); extern int fp_high_losum_p (rtx); +extern bool sparc_tls_referenced_p (rtx); extern int mem_min_alignment (rtx, int); extern int pic_address_needs_scratch (rtx); extern int reg_unused_after (rtx, rtx); diff --git a/gcc/config/sparc/sparc.c b/gcc/config/sparc/sparc.c index af920b30734..1958f3f3982 100644 --- a/gcc/config/sparc/sparc.c +++ b/gcc/config/sparc/sparc.c @@ -864,17 +864,6 @@ fp_high_losum_p (rtx op) return 0; } -/* If OP is a SYMBOL_REF of a thread-local symbol, return its TLS mode, - otherwise return 0. */ - -int -tls_symbolic_operand (rtx op) -{ - if (GET_CODE (op) != SYMBOL_REF) - return 0; - return SYMBOL_REF_TLS_MODEL (op); -} - /* Expand a move instruction. Return true if all work is done. */ bool @@ -895,9 +884,31 @@ sparc_expand_move (enum machine_mode mode, rtx *operands) } /* Fixup TLS cases. */ - if (tls_symbolic_operand (operands [1])) - operands[1] = legitimize_tls_address (operands[1]); + if (TARGET_HAVE_TLS + && CONSTANT_P (operands[1]) + && GET_CODE (operands[1]) != HIGH + && sparc_tls_referenced_p (operands [1])) + { + rtx sym = operands[1]; + rtx addend = NULL; + if (GET_CODE (sym) == CONST && GET_CODE (XEXP (sym, 0)) == PLUS) + { + addend = XEXP (XEXP (sym, 0), 1); + sym = XEXP (XEXP (sym, 0), 0); + } + + gcc_assert (SPARC_SYMBOL_REF_TLS_P (sym)); + + sym = legitimize_tls_address (sym); + if (addend) + { + sym = gen_rtx_PLUS (mode, sym, addend); + sym = force_operand (sym, operands[0]); + } + operands[1] = sym; + } + /* Fixup PIC cases. */ if (flag_pic && CONSTANT_P (operands[1])) { @@ -2725,7 +2736,7 @@ legitimate_constant_p (rtx x) /* Offsets of TLS symbols are never valid. Discourage CSE from creating them. */ if (GET_CODE (inner) == PLUS - && tls_symbolic_operand (XEXP (inner, 0))) + && SPARC_SYMBOL_REF_TLS_P (XEXP (inner, 0))) return false; break; @@ -2792,10 +2803,10 @@ legitimate_pic_operand_p (rtx x) { if (pic_address_needs_scratch (x)) return false; - if (tls_symbolic_operand (x) + if (SPARC_SYMBOL_REF_TLS_P (x) || (GET_CODE (x) == CONST && GET_CODE (XEXP (x, 0)) == PLUS - && tls_symbolic_operand (XEXP (XEXP (x, 0), 0)))) + && SPARC_SYMBOL_REF_TLS_P (XEXP (XEXP (x, 0), 0)))) return false; return true; } @@ -2833,7 +2844,7 @@ legitimate_address_p (enum machine_mode mode, rtx addr, int strict) && GET_CODE (rs2) != SUBREG && GET_CODE (rs2) != LO_SUM && GET_CODE (rs2) != MEM - && !tls_symbolic_operand (rs2) + && ! SPARC_SYMBOL_REF_TLS_P (rs2) && (! symbolic_operand (rs2, VOIDmode) || mode == Pmode) && (GET_CODE (rs2) != CONST_INT || SMALL_INT (rs2))) || ((REG_P (rs1) @@ -2873,7 +2884,7 @@ legitimate_address_p (enum machine_mode mode, rtx addr, int strict) rs2 = NULL; imm1 = XEXP (rs1, 1); rs1 = XEXP (rs1, 0); - if (! CONSTANT_P (imm1) || tls_symbolic_operand (rs1)) + if (! CONSTANT_P (imm1) || SPARC_SYMBOL_REF_TLS_P (rs1)) return 0; } } @@ -2882,7 +2893,7 @@ legitimate_address_p (enum machine_mode mode, rtx addr, int strict) rs1 = XEXP (addr, 0); imm1 = XEXP (addr, 1); - if (! CONSTANT_P (imm1) || tls_symbolic_operand (rs1)) + if (! CONSTANT_P (imm1) || SPARC_SYMBOL_REF_TLS_P (rs1)) return 0; /* We can't allow TFmode in 32-bit mode, because an offset greater @@ -2931,6 +2942,7 @@ legitimate_address_p (enum machine_mode mode, rtx addr, int strict) /* Construct the SYMBOL_REF for the tls_get_offset function. */ static GTY(()) rtx sparc_tls_symbol; + static rtx sparc_tls_get_addr (void) { @@ -2957,6 +2969,24 @@ sparc_tls_got (void) return temp; } +/* Return 1 if *X is a thread-local symbol. */ + +static int +sparc_tls_symbol_ref_1 (rtx *x, void *data ATTRIBUTE_UNUSED) +{ + return SPARC_SYMBOL_REF_TLS_P (*x); +} + +/* Return 1 if X contains a thread-local symbol. */ + +bool +sparc_tls_referenced_p (rtx x) +{ + if (!TARGET_HAVE_TLS) + return false; + + return for_each_rtx (&x, &sparc_tls_symbol_ref_1, 0); +} /* ADDR contains a thread-local SYMBOL_REF. Generate code to compute this (thread-local) address. */ @@ -3219,7 +3249,7 @@ legitimize_address (rtx x, rtx oldx ATTRIBUTE_UNUSED, enum machine_mode mode) if (x != orig_x && legitimate_address_p (mode, x, FALSE)) return x; - if (tls_symbolic_operand (x)) + if (SPARC_SYMBOL_REF_TLS_P (x)) x = legitimize_tls_address (x); else if (flag_pic) x = legitimize_pic_address (x, mode, 0); diff --git a/gcc/config/sparc/sparc.h b/gcc/config/sparc/sparc.h index 0e0aea211ff..9fcee127385 100644 --- a/gcc/config/sparc/sparc.h +++ b/gcc/config/sparc/sparc.h @@ -2358,6 +2358,9 @@ extern int sparc_indent_opcode; sparc_output_dwarf_dtprel (FILE, SIZE, X) #endif +#define SPARC_SYMBOL_REF_TLS_P(RTX) \ + (GET_CODE (RTX) == SYMBOL_REF && SYMBOL_REF_TLS_MODEL (RTX) != 0) + #define PRINT_OPERAND_PUNCT_VALID_P(CHAR) \ ((CHAR) == '#' || (CHAR) == '*' || (CHAR) == '(' \ || (CHAR) == ')' || (CHAR) == '_' || (CHAR) == '&') |