Hi, Jiong pointed out privately that there was a thinko in the way in which the global state was being set and reset. I don't like adding such global state but ....
Tested on aarch64-none-elf with no regressions Bootstrapped and regression tested on aarch64-none-linux-gnu Ok to apply ? regards Ramana 2015-10-15 Ramana Radhakrishnan <ramana.radhakrish...@arm.com> PR target/63304 * config/aarch64/aarch64.c (aarch64_nopcrelative_literal_loads): New. (aarch64_expand_mov_immediate): Use aarch64_nopcrelative_literal_loads. (aarch64_classify_address): Likewise. (aarch64_secondary_reload): Likewise. (aarch64_override_options_after_change_1): Adjust. * config/aarch64/aarch64.md (aarch64_reload_movcp<GPF_TF:mode><P:mode>): Use aarch64_nopcrelative_literal_loads. (aarch64_reload_movcp<VALL:mode><P:mode>): Likewise. * config/aarch64/aarch64-protos.h (aarch64_nopcrelative_literal_loads): Declare 2015-10-15 Jiong Wang <jiong.w...@arm.com> Ramana Radhakrishnan <ramana.radhakrish...@arm.com> PR target/63304 * gcc.target/aarch64/pr63304-1.c: New test. --- gcc/config/aarch64/aarch64-protos.h | 1 + gcc/config/aarch64/aarch64.c | 21 +++++++------ gcc/config/aarch64/aarch64.md | 4 +-- gcc/testsuite/gcc.target/aarch64/pr63304-1.c | 47 ++++++++++++++++++++++++++++ 4 files changed, 62 insertions(+), 11 deletions(-) create mode 100644 gcc/testsuite/gcc.target/aarch64/pr63304-1.c diff --git a/gcc/config/aarch64/aarch64-protos.h b/gcc/config/aarch64/aarch64-protos.h index baaf1bd..bf501c8 100644 --- a/gcc/config/aarch64/aarch64-protos.h +++ b/gcc/config/aarch64/aarch64-protos.h @@ -400,4 +400,5 @@ int aarch64_ccmp_mode_to_code (enum machine_mode mode); bool extract_base_offset_in_addr (rtx mem, rtx *base, rtx *offset); bool aarch64_operands_ok_for_ldpstp (rtx *, bool, enum machine_mode); bool aarch64_operands_adjust_ok_for_ldpstp (rtx *, bool, enum machine_mode); +extern bool aarch64_nopcrelative_literal_loads; #endif /* GCC_AARCH64_PROTOS_H */ diff --git a/gcc/config/aarch64/aarch64.c b/gcc/config/aarch64/aarch64.c index 5130e37..f9664f5 100644 --- a/gcc/config/aarch64/aarch64.c +++ b/gcc/config/aarch64/aarch64.c @@ -163,6 +163,9 @@ enum aarch64_processor aarch64_tune = cortexa53; /* Mask to specify which instruction scheduling options should be used. */ unsigned long aarch64_tune_flags = 0; +/* Global flag for PC relative loads. */ +bool aarch64_nopcrelative_literal_loads; + /* Support for command line parsing of boolean flags in the tuning structures. */ struct aarch64_flag_desc @@ -1551,7 +1554,7 @@ aarch64_expand_mov_immediate (rtx dest, rtx imm) we need to expand the literal pool access carefully. This is something that needs to be done in a number of places, so could well live as a separate function. */ - if (nopcrelative_literal_loads) + if (aarch64_nopcrelative_literal_loads) { gcc_assert (can_create_pseudo_p ()); base = gen_reg_rtx (ptr_mode); @@ -3665,7 +3668,7 @@ aarch64_classify_address (struct aarch64_address_info *info, return ((GET_CODE (sym) == LABEL_REF || (GET_CODE (sym) == SYMBOL_REF && CONSTANT_POOL_ADDRESS_P (sym) - && !nopcrelative_literal_loads))); + && !aarch64_nopcrelative_literal_loads))); } return false; @@ -4899,7 +4902,7 @@ aarch64_secondary_reload (bool in_p ATTRIBUTE_UNUSED, rtx x, if (MEM_P (x) && GET_CODE (x) == SYMBOL_REF && CONSTANT_POOL_ADDRESS_P (x) && (SCALAR_FLOAT_MODE_P (GET_MODE (x)) || targetm.vector_mode_supported_p (GET_MODE (x))) - && nopcrelative_literal_loads) + && aarch64_nopcrelative_literal_loads) { sri->icode = aarch64_constant_pool_reload_icode (mode); return NO_REGS; @@ -7555,21 +7558,21 @@ aarch64_override_options_after_change_1 (struct gcc_options *opts) /* If nopcrelative_literal_loads is set on the command line, this implies that the user asked for PC relative literal loads. */ - if (nopcrelative_literal_loads == 1) - nopcrelative_literal_loads = 0; + if (opts->x_nopcrelative_literal_loads == 1) + aarch64_nopcrelative_literal_loads = false; /* If it is not set on the command line, we default to no pc relative literal loads. */ - if (nopcrelative_literal_loads == 2) - nopcrelative_literal_loads = 1; + if (opts->x_nopcrelative_literal_loads == 2) + aarch64_nopcrelative_literal_loads = true; /* In the tiny memory model it makes no sense to disallow non PC relative literal pool loads as many other things will break anyway. */ - if (nopcrelative_literal_loads + if (opts->x_nopcrelative_literal_loads && (aarch64_cmodel == AARCH64_CMODEL_TINY || aarch64_cmodel == AARCH64_CMODEL_TINY_PIC)) - nopcrelative_literal_loads = 0; + aarch64_nopcrelative_literal_loads = false; } /* 'Unpack' up the internal tuning structs and update the options diff --git a/gcc/config/aarch64/aarch64.md b/gcc/config/aarch64/aarch64.md index 208f58f..e06c330 100644 --- a/gcc/config/aarch64/aarch64.md +++ b/gcc/config/aarch64/aarch64.md @@ -4491,7 +4491,7 @@ [(set (match_operand:GPF_TF 0 "register_operand" "=w") (mem:GPF_TF (match_operand 1 "aarch64_constant_pool_symref" "S"))) (clobber (match_operand:P 2 "register_operand" "=&r"))] - "TARGET_FLOAT && nopcrelative_literal_loads" + "TARGET_FLOAT && aarch64_nopcrelative_literal_loads" { aarch64_expand_mov_immediate (operands[2], XEXP (operands[1], 0)); emit_move_insn (operands[0], gen_rtx_MEM (<GPF_TF:MODE>mode, operands[2])); @@ -4504,7 +4504,7 @@ [(set (match_operand:VALL 0 "register_operand" "=w") (mem:VALL (match_operand 1 "aarch64_constant_pool_symref" "S"))) (clobber (match_operand:P 2 "register_operand" "=&r"))] - "TARGET_FLOAT && nopcrelative_literal_loads" + "TARGET_FLOAT && aarch64_nopcrelative_literal_loads" { aarch64_expand_mov_immediate (operands[2], XEXP (operands[1], 0)); emit_move_insn (operands[0], gen_rtx_MEM (<VALL:MODE>mode, operands[2])); diff --git a/gcc/testsuite/gcc.target/aarch64/pr63304-1.c b/gcc/testsuite/gcc.target/aarch64/pr63304-1.c new file mode 100644 index 0000000..fa0fb56 --- /dev/null +++ b/gcc/testsuite/gcc.target/aarch64/pr63304-1.c @@ -0,0 +1,47 @@ +/* { dg-do assemble } */ +/* { dg-options "-O1 --save-temps" } */ +#pragma GCC push_options +#pragma GCC target ("+nothing+simd, cmodel=small") + +int +cal (float a) +{ + float b = 1.2; + float c = 2.2; + if ((a + b) != c) + return 0; + else + return 1; +} + +#pragma GCC push_options + +#pragma GCC target ("cmodel=large") + +int +cal2 (float a) +{ + + float b = 1.2; + float c = 2.2; + if ((a + b) != c) + return 0; + else + return 1; +} + +#pragma GCC pop_options + +int +cal3 (float a) +{ + + float b = 1.2; + float c = 2.2; + if ((a + b) != c) + return 0; + else + return 1; +} + +/* { dg-final { scan-assembler-times "adrp" 6 } } */ -- 1.9.1