diff options
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/ChangeLog | 5 | ||||
-rw-r--r-- | gcc/config/nds32/nds32.c | 48 |
2 files changed, 41 insertions, 12 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 6166c08..d358973 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,5 +1,10 @@ 2015-01-13 Chung-Ju Wu <jasonwucj@gmail.com> + * config/nds32/nds32.c (nds32_legitimate_address_p): Consider + TARGET_CMODEL_LARGE and TARGET_CMODEL_MEDIUM cases. + +2015-01-13 Chung-Ju Wu <jasonwucj@gmail.com> + * config/nds32/nds32.h (NDS32_SYMBOL_FLAG_RODATA): Define our own target-specific symbol_ref flag. (NDS32_SYMBOL_REF_RODATA_P): Define it to check if the symbol_ref diff --git a/gcc/config/nds32/nds32.c b/gcc/config/nds32/nds32.c index 5128bfa..192816f 100644 --- a/gcc/config/nds32/nds32.c +++ b/gcc/config/nds32/nds32.c @@ -1961,24 +1961,27 @@ nds32_legitimate_address_p (machine_mode mode, rtx x, bool strict) return nds32_address_register_rtx_p (x, strict); case SYMBOL_REF: - - if (!TARGET_GP_DIRECT + /* (mem (symbol_ref A)) => [symbol_ref] */ + /* If -mcmodel=large, the 'symbol_ref' is not a valid address + during or after LRA/reload phase. */ + if (TARGET_CMODEL_LARGE && (reload_completed || reload_in_progress || lra_in_progress)) return false; - - /* (mem (symbol_ref A)) => [symbol_ref] */ - return !currently_expanding_to_rtl; - - case CONST: - - if (!TARGET_GP_DIRECT + /* If -mcmodel=medium and the symbol references to rodata section, + the 'symbol_ref' is not a valid address during or after + LRA/reload phase. */ + if (TARGET_CMODEL_MEDIUM + && NDS32_SYMBOL_REF_RODATA_P (x) && (reload_completed || reload_in_progress || lra_in_progress)) return false; + return true; + + case CONST: /* (mem (const (...))) => [ + const_addr ], where const_addr = symbol_ref + const_int */ if (GET_CODE (XEXP (x, 0)) == PLUS) @@ -1989,9 +1992,30 @@ nds32_legitimate_address_p (machine_mode mode, rtx x, bool strict) rtx op1 = XEXP (plus_op, 1); if (GET_CODE (op0) == SYMBOL_REF && CONST_INT_P (op1)) - return true; - else - return false; + { + /* Now we see the [ + const_addr ] pattern, but we need + some further checking. */ + /* If -mcmodel=large, the 'const_addr' is not a valid address + during or after LRA/reload phase. */ + if (TARGET_CMODEL_LARGE + && (reload_completed + || reload_in_progress + || lra_in_progress)) + return false; + /* If -mcmodel=medium and the symbol references to rodata section, + the 'const_addr' is not a valid address during or after + LRA/reload phase. */ + if (TARGET_CMODEL_MEDIUM + && NDS32_SYMBOL_REF_RODATA_P (op0) + && (reload_completed + || reload_in_progress + || lra_in_progress)) + return false; + + /* At this point we can make sure 'const_addr' is a + valid address. */ + return true; + } } return false; |