MIPS: PR target/78176 add -mlxc1-sxc1.

gcc/

	PR target/78176
	* config.gcc (supported_defaults): Add lxc1-sxc1.
	(with_lxc1_sxc1): Add validation.
	(all_defaults): Add lxc1-sxc1.
	* config/mips/mips.opt (mlxc1-sxc1): New option.
	* gcc/config/mips/mips.h (OPTION_DEFAULT_SPECS): Add a default for
	mlxc1-sxc1.
	(TARGET_CPU_CPP_BUILTINS): Add builtin_define for
	__mips_no_lxc1_sxc1.
	(ISA_HAS_LXC1_SXC1): Gate with mips_lxc1_sxc1.
	* gcc/doc/invoke.texi (-mlxc1-sxc1): Document the new option.
	* doc/install.texi (--with-lxc1-sxc1): Document the new option.

gcc/testsuite/

	* gcc.target/mips/lxc1-sxc1-1.c: New file.
	* gcc.target/mips/lxc1-sxc1-2.c: Likewise.
	* gcc.target/mips/mips.exp (mips_option_groups): Add ghost option
	HAS_LXC1.
	(mips_option_groups): Add -m[no-]lxc1-sxc1.
	(mips-dg-init): Detect default -mno-lxc1-sxc1.
	(mips-dg-options): Handle HAS_LXC1 arch upgrade/downgrade.

From-SVN: r244640
This commit is contained in:
Matthew Fortune 2017-01-19 16:05:59 +00:00
parent a08895999d
commit ab6b44cb22
10 changed files with 209 additions and 5 deletions

View File

@ -1,3 +1,18 @@
2017-01-19 Doug Gilmore <doug.gilmore@imgtec.com>
PR target/78176
* config.gcc (supported_defaults): Add lxc1-sxc1.
(with_lxc1_sxc1): Add validation.
(all_defaults): Add lxc1-sxc1.
* config/mips/mips.opt (mlxc1-sxc1): New option.
* gcc/config/mips/mips.h (OPTION_DEFAULT_SPECS): Add a default for
mlxc1-sxc1.
(TARGET_CPU_CPP_BUILTINS): Add builtin_define for
__mips_no_lxc1_sxc1.
(ISA_HAS_LXC1_SXC1): Gate with mips_lxc1_sxc1.
* gcc/doc/invoke.texi (-mlxc1-sxc1): Document the new option.
* doc/install.texi (--with-lxc1-sxc1): Document the new option.
2017-01-19 Richard Biener <rguenther@suse.de> 2017-01-19 Richard Biener <rguenther@suse.de>
PR tree-optimization/72488 PR tree-optimization/72488

View File

@ -3940,7 +3940,7 @@ case "${target}" in
;; ;;
mips*-*-*) mips*-*-*)
supported_defaults="abi arch arch_32 arch_64 float fpu nan fp_32 odd_spreg_32 tune tune_32 tune_64 divide llsc mips-plt synci" supported_defaults="abi arch arch_32 arch_64 float fpu nan fp_32 odd_spreg_32 tune tune_32 tune_64 divide llsc mips-plt synci lxc1-sxc1"
case ${with_float} in case ${with_float} in
"" | soft | hard) "" | soft | hard)
@ -4063,6 +4063,21 @@ case "${target}" in
exit 1 exit 1
;; ;;
esac esac
case ${with_lxc1_sxc1} in
yes)
with_lxc1_sxc1=lxc1-sxc1
;;
no)
with_lxc1_sxc1=no-lxc1-sxc1
;;
"")
;;
*)
echo "Unknown lxc1-sxc1 type used in --with-lxc1-sxc1" 1>&2
exit 1
;;
esac
;; ;;
nds32*-*-*) nds32*-*-*)
@ -4496,7 +4511,7 @@ case ${target} in
esac esac
t= t=
all_defaults="abi cpu cpu_32 cpu_64 arch arch_32 arch_64 tune tune_32 tune_64 schedule float mode fpu nan fp_32 odd_spreg_32 divide llsc mips-plt synci tls" all_defaults="abi cpu cpu_32 cpu_64 arch arch_32 arch_64 tune tune_32 tune_64 schedule float mode fpu nan fp_32 odd_spreg_32 divide llsc mips-plt synci tls lxc1-sxc1"
for option in $all_defaults for option in $all_defaults
do do
eval "val=\$with_"`echo $option | sed s/-/_/g` eval "val=\$with_"`echo $option | sed s/-/_/g`

View File

@ -637,6 +637,8 @@ struct mips_cpu_info {
\ \
if (TARGET_CACHE_BUILTIN) \ if (TARGET_CACHE_BUILTIN) \
builtin_define ("__GCC_HAVE_BUILTIN_MIPS_CACHE"); \ builtin_define ("__GCC_HAVE_BUILTIN_MIPS_CACHE"); \
if (!ISA_HAS_LXC1_SXC1) \
builtin_define ("__mips_no_lxc1_sxc1"); \
} \ } \
while (0) while (0)
@ -866,7 +868,8 @@ struct mips_cpu_info {
{"divide", "%{!mdivide-traps:%{!mdivide-breaks:-mdivide-%(VALUE)}}" }, \ {"divide", "%{!mdivide-traps:%{!mdivide-breaks:-mdivide-%(VALUE)}}" }, \
{"llsc", "%{!mllsc:%{!mno-llsc:-m%(VALUE)}}" }, \ {"llsc", "%{!mllsc:%{!mno-llsc:-m%(VALUE)}}" }, \
{"mips-plt", "%{!mplt:%{!mno-plt:-m%(VALUE)}}" }, \ {"mips-plt", "%{!mplt:%{!mno-plt:-m%(VALUE)}}" }, \
{"synci", "%{!msynci:%{!mno-synci:-m%(VALUE)}}" } {"synci", "%{!msynci:%{!mno-synci:-m%(VALUE)}}" }, \
{"lxc1-sxc1", "%{!mlxc1-sxc1:%{!mno-lxc1-sxc1:-m%(VALUE)}}" } \
/* A spec that infers the: /* A spec that infers the:
-mnan=2008 setting from a -mips argument, -mnan=2008 setting from a -mips argument,
@ -1036,7 +1039,8 @@ struct mips_cpu_info {
/* ISA has floating-point indexed load and store instructions /* ISA has floating-point indexed load and store instructions
(LWXC1, LDXC1, SWXC1 and SDXC1). */ (LWXC1, LDXC1, SWXC1 and SDXC1). */
#define ISA_HAS_LXC1_SXC1 ISA_HAS_FP4 #define ISA_HAS_LXC1_SXC1 (ISA_HAS_FP4 \
&& mips_lxc1_sxc1)
/* ISA has paired-single instructions. */ /* ISA has paired-single instructions. */
#define ISA_HAS_PAIRED_SINGLE ((ISA_MIPS64 \ #define ISA_HAS_PAIRED_SINGLE ((ISA_MIPS64 \

View File

@ -388,6 +388,10 @@ mlra
Target Report Var(mips_lra_flag) Init(1) Save Target Report Var(mips_lra_flag) Init(1) Save
Use LRA instead of reload. Use LRA instead of reload.
mlxc1-sxc1
Target Report Var(mips_lxc1_sxc1) Init(1)
Use lwxc1/swxc1/ldxc1/sdxc1 instructions where applicable.
mtune= mtune=
Target RejectNegative Joined Var(mips_tune_option) ToLower Enum(mips_arch_opt_value) Target RejectNegative Joined Var(mips_tune_option) ToLower Enum(mips_arch_opt_value)
-mtune=PROCESSOR Optimize the output for PROCESSOR. -mtune=PROCESSOR Optimize the output for PROCESSOR.

View File

@ -1375,6 +1375,25 @@ On MIPS targets, make @option{-msynci} the default when no
On MIPS targets, make @option{-mno-synci} the default when no On MIPS targets, make @option{-mno-synci} the default when no
@option{-msynci} option is passed. This is the default. @option{-msynci} option is passed. This is the default.
@item --with-lxc1-sxc1
On MIPS targets, make @option{-mlxc1-sxc1} the default when no
@option{-mno-lxc1-sxc1} option is passed. This is the default.
@item --without-lxc1-sxc1
On MIPS targets, make @option{-mno-lxc1-sxc1} the default when no
@option{-mlxc1-sxc1} option is passed. The indexed load/store
instructions are not directly a problem but can lead to unexpected
behaviour when deployed in an application intended for a 32-bit address
space but run on a 64-bit processor. The issue is seen because all
known MIPS 64-bit Linux kernels execute o32 and n32 applications
with 64-bit addressing enabled which affects the overflow behaviour
of the indexed addressing mode. GCC will assume that ordinary
32-bit arithmetic overflow behaviour is the same whether performed
as an @code{addu} instruction or as part of the address calculation
in @code{lwxc1} type instructions. This assumption holds true in a
pure 32-bit environment and can hold true in a 64-bit environment if
the address space is accurately set to be 32-bit for o32 and n32.
@item --with-mips-plt @item --with-mips-plt
On MIPS targets, make use of copy relocations and PLTs. On MIPS targets, make use of copy relocations and PLTs.
These features are extensions to the traditional These features are extensions to the traditional

View File

@ -19932,6 +19932,12 @@ it is unused.
This optimization is off by default at all optimization levels. This optimization is off by default at all optimization levels.
@item -mlxc1-sxc1
@itemx -mno-lxc1-sxc1
@opindex mlxc1-sxc1
When applicable, enable (disable) the generation of @code{lwxc1},
@code{swxc1}, @code{ldxc1}, @code{sdxc1} instructions. Enabled by default.
@end table @end table
@node MMIX Options @node MMIX Options

View File

@ -1,3 +1,14 @@
2017-01-19 Matthew Fortune <matthew.fortune@imgtec.com>
PR target/78176
* gcc.target/mips/lxc1-sxc1-1.c: New file.
* gcc.target/mips/lxc1-sxc1-2.c: Likewise.
* gcc.target/mips/mips.exp (mips_option_groups): Add ghost option
HAS_LXC1.
(mips_option_groups): Add -m[no-]lxc1-sxc1.
(mips-dg-init): Detect default -mno-lxc1-sxc1.
(mips-dg-options): Handle HAS_LXC1 arch upgrade/downgrade.
2017-01-19 Andre Vehreschild <vehre@gcc.gnu.org> 2017-01-19 Andre Vehreschild <vehre@gcc.gnu.org>
PR fortran/70696 PR fortran/70696

View File

@ -0,0 +1,60 @@
/* { dg-options "(HAS_LXC1) -mno-lxc1-sxc1" } */
/* { dg-final { scan-assembler-not "\tldxc1\t" } } */
/* { dg-final { scan-assembler-not "\tsdxc1\t" } } */
#ifndef __mips_no_lxc1_sxc1
#error missing definition of __mips_no_lxc1_sxc1
#endif
double ldexp(double x, int exp);
typedef struct
{
double** rows;
} d_mat_struct;
typedef d_mat_struct d_mat_t[1];
#define d_mat_entry(mat,i,j) (*((mat)->rows[i] + (j)))
double __attribute__((noinline))
ldxc1_test (int kappa, int zeros, double ctt, int* expo, d_mat_t r, double* s)
{
int kappa2 = kappa;
double tmp = 0.0;
do
{
kappa--;
if (kappa > zeros + 1)
{
tmp = d_mat_entry(r, kappa - 1, kappa - 1) * ctt;
tmp = ldexp(tmp, (expo[kappa - 1] - expo[kappa2]));
}
}
while ((kappa >= zeros + 2) && (s[kappa - 1] <= tmp));
return tmp;
}
#define SIZE 20
int main(void)
{
int kappa = SIZE - 1;
int zeros = 1;
double ctt = 2;
int expo[SIZE] = {0};
double s[SIZE] = {0};
double rows_data[SIZE][SIZE] = {0};
double* rows[SIZE];
for (int i = 0; i < SIZE; i++)
rows[i] = rows_data[i];
d_mat_t r = { rows };
ldxc1_test(kappa, zeros, ctt, expo, r, s);
return 0;
}

View File

@ -0,0 +1,60 @@
/* { dg-options "(HAS_LXC1) -mlxc1-sxc1" } */
/* { dg-skip-if "code quality test" { *-*-* } { "-O0" } { "" } } */
/* { dg-final { scan-assembler "\tldxc1\t" } } */
#ifdef __mips_no_lxc1_sxc1
#error unexpected definition of __mips_no_lxc1_sxc1
#endif
double ldexp(double x, int exp);
typedef struct
{
double** rows;
} d_mat_struct;
typedef d_mat_struct d_mat_t[1];
#define d_mat_entry(mat,i,j) (*((mat)->rows[i] + (j)))
double __attribute__((noinline))
ldxc1_test (int kappa, int zeros, double ctt, int* expo, d_mat_t r, double* s)
{
int kappa2 = kappa;
double tmp = 0.0;
do
{
kappa--;
if (kappa > zeros + 1)
{
tmp = d_mat_entry(r, kappa - 1, kappa - 1) * ctt;
tmp = ldexp(tmp, (expo[kappa - 1] - expo[kappa2]));
}
}
while ((kappa >= zeros + 2) && (s[kappa - 1] <= tmp));
return tmp;
}
#define SIZE 20
int main(void)
{
int kappa = SIZE - 1;
int zeros = 1;
double ctt = 2;
int expo[SIZE] = {0};
double s[SIZE] = {0};
double rows_data[SIZE][SIZE] = {0};
double* rows[SIZE];
for (int i = 0; i < SIZE; i++)
rows[i] = rows_data[i];
d_mat_t r = { rows };
ldxc1_test(kappa, zeros, ctt, expo, r, s);
return 0;
}

View File

@ -258,6 +258,7 @@ set mips_option_groups {
madd "HAS_MADD" madd "HAS_MADD"
maddps "HAS_MADDPS" maddps "HAS_MADDPS"
lsa "(|!)HAS_LSA" lsa "(|!)HAS_LSA"
lxc1 "HAS_LXC1"
section_start "-Wl,--section-start=.*" section_start "-Wl,--section-start=.*"
frame-header "-mframe-header-opt|-mno-frame-header-opt" frame-header "-mframe-header-opt|-mno-frame-header-opt"
stack-protector "-fstack-protector" stack-protector "-fstack-protector"
@ -282,6 +283,7 @@ foreach option {
gpopt gpopt
local-sdata local-sdata
long-calls long-calls
lxc1-sxc1
paired-single paired-single
plt plt
shared shared
@ -855,6 +857,12 @@ proc mips-dg-init {} {
"-mno-smartmips", "-mno-smartmips",
#endif #endif
#ifdef __mips_no_lxc1_sxc1
"-mno-lxc1-sxc1",
#else
"-mlxc1-sxc1"
#endif
#ifdef __mips_synci #ifdef __mips_synci
"-msynci", "-msynci",
#else #else
@ -1173,7 +1181,8 @@ proc mips-dg-options { args } {
# #
# #
} elseif { $isa < 4 } elseif { $isa < 4
&& [mips_have_test_option_p options "HAS_MOVN"] } { && ([mips_have_test_option_p options "HAS_LXC1"]
|| [mips_have_test_option_p options "HAS_MOVN"]) } {
mips_make_test_option options "-mips4" mips_make_test_option options "-mips4"
# We need MIPS III or higher for: # We need MIPS III or higher for:
# #
@ -1214,6 +1223,7 @@ proc mips-dg-options { args } {
|| [mips_have_test_option_p options "-mfp32"] || [mips_have_test_option_p options "-mfp32"]
|| [mips_have_test_option_p options "-mfix-r10000"] || [mips_have_test_option_p options "-mfix-r10000"]
|| [mips_have_test_option_p options "NOT_HAS_DMUL"] || [mips_have_test_option_p options "NOT_HAS_DMUL"]
|| [mips_have_test_option_p options "HAS_LXC1"]
|| [mips_have_test_option_p options "HAS_MOVN"] || [mips_have_test_option_p options "HAS_MOVN"]
|| [mips_have_test_option_p options "HAS_MADD"] || [mips_have_test_option_p options "HAS_MADD"]
|| [mips_have_test_option_p options "-mpaired-single"] || [mips_have_test_option_p options "-mpaired-single"]