diff options
author | Michael Matz <matz@suse.de> | 2011-10-06 13:27:47 +0000 |
---|---|---|
committer | Michael Matz <matz@gcc.gnu.org> | 2011-10-06 13:27:47 +0000 |
commit | b86b9f447472aa9e1ad05dbbabe3aa1b09ca3573 (patch) | |
tree | eb347aa6978471e390f71a0cd82bf907b8cf2484 /gcc | |
parent | 16340e8601a250e5024d999e05a192b992b8475d (diff) | |
download | gcc-b86b9f447472aa9e1ad05dbbabe3aa1b09ca3573.zip gcc-b86b9f447472aa9e1ad05dbbabe3aa1b09ca3573.tar.gz gcc-b86b9f447472aa9e1ad05dbbabe3aa1b09ca3573.tar.bz2 |
i386.opt (recip_mask, [...]): New variables and cl_target member.
* i386/i386.opt (recip_mask, recip_mask_explicit,
x_recip_mask_explicit): New variables and cl_target member.
(mrecip=): New option.
* i386/i386.h (RECIP_MASK_DIV, RECIP_MASK_SQRT, RECIP_MASK_VEC_DIV,
RECIP_MASK_VEC_SQRT, RECIP_MASK_ALL, RECIP_MASK_NONE): New bitmasks.
(TARGET_RECIP_DIV, TARGET_RECIP_SQRT, TARGET_RECIP_VEC_DIV,
TARGET_RECIP_VEC_SQRT): New tests.
* i386/i386.md (divsf3): Check TARGET_RECIP_DIV.
(sqrt<mode>2): Check TARGET_RECIP_SQRT.
* i386/sse.md (div<mode>3): Check TARGET_RECIP_VEC_DIV.
(sqrt<mode>2): Check TARGET_RECIP_VEC_SQRT.
* i386/i386.c (ix86_option_override_internal): Set recip_mask
for -mrecip and -mrecip=options.
(ix86_function_specific_save): Save recip_mask_explicit.
(ix86_function_specific_restore): Restore recip_mask_explicit.
* doc/invoke.texi (ix86 Options): Document the new option.
From-SVN: r179608
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/ChangeLog | 20 | ||||
-rw-r--r-- | gcc/config/i386/i386.c | 68 | ||||
-rw-r--r-- | gcc/config/i386/i386.h | 13 | ||||
-rw-r--r-- | gcc/config/i386/i386.md | 8 | ||||
-rw-r--r-- | gcc/config/i386/i386.opt | 13 | ||||
-rw-r--r-- | gcc/config/i386/sse.md | 8 | ||||
-rw-r--r-- | gcc/doc/invoke.texi | 20 |
7 files changed, 145 insertions, 5 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 2747f2b..7e6bf33 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,23 @@ +2011-10-06 Michael Matz <matz@suse.de> + + * i386/i386.opt (recip_mask, recip_mask_explicit, + x_recip_mask_explicit): New variables and cl_target member. + (mrecip=): New option. + * i386/i386.h (RECIP_MASK_DIV, RECIP_MASK_SQRT, RECIP_MASK_VEC_DIV, + RECIP_MASK_VEC_SQRT, RECIP_MASK_ALL, RECIP_MASK_NONE): New bitmasks. + (TARGET_RECIP_DIV, TARGET_RECIP_SQRT, TARGET_RECIP_VEC_DIV, + TARGET_RECIP_VEC_SQRT): New tests. + * i386/i386.md (divsf3): Check TARGET_RECIP_DIV. + (sqrt<mode>2): Check TARGET_RECIP_SQRT. + * i386/sse.md (div<mode>3): Check TARGET_RECIP_VEC_DIV. + (sqrt<mode>2): Check TARGET_RECIP_VEC_SQRT. + * i386/i386.c (ix86_option_override_internal): Set recip_mask + for -mrecip and -mrecip=options. + (ix86_function_specific_save): Save recip_mask_explicit. + (ix86_function_specific_restore): Restore recip_mask_explicit. + + * doc/invoke.texi (ix86 Options): Document the new option. + 2011-10-06 Bernd Schmidt <bernds@codesourcery.com> PR target/49049 diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c index faad3a5..688fba1 100644 --- a/gcc/config/i386/i386.c +++ b/gcc/config/i386/i386.c @@ -3057,6 +3057,22 @@ ix86_option_override_internal (bool main_args_p) PTA_64BIT /* flags are only used for -march switch. */ }, }; + /* -mrecip options. */ + static struct + { + const char *string; /* option name */ + unsigned int mask; /* mask bits to set */ + } + const recip_options[] = + { + { "all", RECIP_MASK_ALL }, + { "none", RECIP_MASK_NONE }, + { "div", RECIP_MASK_DIV }, + { "sqrt", RECIP_MASK_SQRT }, + { "vec-div", RECIP_MASK_VEC_DIV }, + { "vec-sqrt", RECIP_MASK_VEC_SQRT }, + }; + int const pta_size = ARRAY_SIZE (processor_alias_table); /* Set up prefix/suffix so the error messages refer to either the command @@ -3814,6 +3830,56 @@ ix86_option_override_internal (bool main_args_p) target_flags &= ~MASK_VZEROUPPER; } + if (ix86_recip_name) + { + char *p = ASTRDUP (ix86_recip_name); + char *q; + unsigned int mask, i; + bool invert; + + while ((q = strtok (p, ",")) != NULL) + { + p = NULL; + if (*q == '!') + { + invert = true; + q++; + } + else + invert = false; + + if (!strcmp (q, "default")) + mask = RECIP_MASK_ALL; + else + { + for (i = 0; i < ARRAY_SIZE (recip_options); i++) + if (!strcmp (q, recip_options[i].string)) + { + mask = recip_options[i].mask; + break; + } + + if (i == ARRAY_SIZE (recip_options)) + { + error ("unknown option for -mrecip=%s", q); + invert = false; + mask = RECIP_MASK_NONE; + } + } + + recip_mask_explicit |= mask; + if (invert) + recip_mask &= ~mask; + else + recip_mask |= mask; + } + } + + if (TARGET_RECIP) + recip_mask |= RECIP_MASK_ALL & ~recip_mask_explicit; + else if (target_flags_explicit & MASK_RECIP) + recip_mask &= ~(RECIP_MASK_ALL & ~recip_mask_explicit); + /* Save the initial options in case the user does function specific options. */ if (main_args_p) @@ -3946,6 +4012,7 @@ ix86_function_specific_save (struct cl_target_option *ptr) ptr->arch_specified = ix86_arch_specified; ptr->x_ix86_isa_flags_explicit = ix86_isa_flags_explicit; ptr->ix86_target_flags_explicit = target_flags_explicit; + ptr->x_recip_mask_explicit = recip_mask_explicit; /* The fields are char but the variables are not; make sure the values fit in the fields. */ @@ -3973,6 +4040,7 @@ ix86_function_specific_restore (struct cl_target_option *ptr) ix86_arch_specified = ptr->arch_specified; ix86_isa_flags_explicit = ptr->x_ix86_isa_flags_explicit; target_flags_explicit = ptr->ix86_target_flags_explicit; + recip_mask_explicit = ptr->x_recip_mask_explicit; /* Recreate the arch feature tests if the arch changed */ if (old_arch != ix86_arch) diff --git a/gcc/config/i386/i386.h b/gcc/config/i386/i386.h index 7d6e058..bd69ec2 100644 --- a/gcc/config/i386/i386.h +++ b/gcc/config/i386/i386.h @@ -2315,6 +2315,19 @@ extern void debug_dispatch_window (int); ((FLAGS) & (IX86_CALLCVT_CDECL | IX86_CALLCVT_STDCALL \ | IX86_CALLCVT_FASTCALL | IX86_CALLCVT_THISCALL)) +#define RECIP_MASK_NONE 0x00 +#define RECIP_MASK_DIV 0x01 +#define RECIP_MASK_SQRT 0x02 +#define RECIP_MASK_VEC_DIV 0x04 +#define RECIP_MASK_VEC_SQRT 0x08 +#define RECIP_MASK_ALL (RECIP_MASK_DIV | RECIP_MASK_SQRT \ + | RECIP_MASK_VEC_DIV | RECIP_MASK_VEC_SQRT) + +#define TARGET_RECIP_DIV ((recip_mask & RECIP_MASK_DIV) != 0) +#define TARGET_RECIP_SQRT ((recip_mask & RECIP_MASK_SQRT) != 0) +#define TARGET_RECIP_VEC_DIV ((recip_mask & RECIP_MASK_VEC_DIV) != 0) +#define TARGET_RECIP_VEC_SQRT ((recip_mask & RECIP_MASK_VEC_SQRT) != 0) + /* Local variables: version-control: t diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md index b8a649c..a11a71b 100644 --- a/gcc/config/i386/i386.md +++ b/gcc/config/i386/i386.md @@ -7062,7 +7062,9 @@ "(TARGET_80387 && X87_ENABLE_ARITH (SFmode)) || TARGET_SSE_MATH" { - if (TARGET_SSE_MATH && TARGET_RECIP && optimize_insn_for_speed_p () + if (TARGET_SSE_MATH + && TARGET_RECIP_DIV + && optimize_insn_for_speed_p () && flag_finite_math_only && !flag_trapping_math && flag_unsafe_math_optimizations) { @@ -13438,7 +13440,9 @@ || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)" { if (<MODE>mode == SFmode - && TARGET_SSE_MATH && TARGET_RECIP && !optimize_function_for_size_p (cfun) + && TARGET_SSE_MATH + && TARGET_RECIP_SQRT + && !optimize_function_for_size_p (cfun) && flag_finite_math_only && !flag_trapping_math && flag_unsafe_math_optimizations) { diff --git a/gcc/config/i386/i386.opt b/gcc/config/i386/i386.opt index 8e4d51b..43009a3 100644 --- a/gcc/config/i386/i386.opt +++ b/gcc/config/i386/i386.opt @@ -31,6 +31,15 @@ HOST_WIDE_INT ix86_isa_flags = TARGET_64BIT_DEFAULT | TARGET_SUBTARGET_ISA_DEFAU Variable HOST_WIDE_INT ix86_isa_flags_explicit +TargetVariable +int recip_mask + +Variable +int recip_mask_explicit + +TargetSave +int x_recip_mask_explicit + ;; Definitions to add to the cl_target_option structure ;; -march= processor TargetSave @@ -373,6 +382,10 @@ mrecip Target Report Mask(RECIP) Save Generate reciprocals instead of divss and sqrtss. +mrecip= +Target Report RejectNegative Joined Var(ix86_recip_name) +Control generation of reciprocal estimates. + mcld Target Report Mask(CLD) Save Generate cld instruction in the function prologue. diff --git a/gcc/config/i386/sse.md b/gcc/config/i386/sse.md index ee9cf0b..88f4d6c 100644 --- a/gcc/config/i386/sse.md +++ b/gcc/config/i386/sse.md @@ -779,7 +779,9 @@ { ix86_fixup_binary_operands_no_copy (DIV, <MODE>mode, operands); - if (TARGET_SSE_MATH && TARGET_RECIP && !optimize_insn_for_size_p () + if (TARGET_SSE_MATH + && TARGET_RECIP_VEC_DIV + && !optimize_insn_for_size_p () && flag_finite_math_only && !flag_trapping_math && flag_unsafe_math_optimizations) { @@ -857,7 +859,9 @@ (sqrt:VF1 (match_operand:VF1 1 "nonimmediate_operand" "")))] "TARGET_SSE" { - if (TARGET_SSE_MATH && TARGET_RECIP && !optimize_insn_for_size_p () + if (TARGET_SSE_MATH + && TARGET_RECIP_VEC_SQRT + && !optimize_insn_for_size_p () && flag_finite_math_only && !flag_trapping_math && flag_unsafe_math_optimizations) { diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi index 0588284..ef7ac68 100644 --- a/gcc/doc/invoke.texi +++ b/gcc/doc/invoke.texi @@ -605,7 +605,9 @@ Objective-C and Objective-C++ Dialects}. -mno-wide-multiply -mrtd -malign-double @gol -mpreferred-stack-boundary=@var{num} @gol -mincoming-stack-boundary=@var{num} @gol --mcld -mcx16 -msahf -mmovbe -mcrc32 -mrecip -mvzeroupper @gol +-mcld -mcx16 -msahf -mmovbe -mcrc32 @gol +-mrecip -mrecip=@var{opt} @gol +-mvzeroupper @gol -mmmx -msse -msse2 -msse3 -mssse3 -msse4.1 -msse4.2 -msse4 -mavx @gol -mavx2 -maes -mpclmul -mfsgsbase -mrdrnd -mf16c -mfma @gol -msse4a -m3dnow -mpopcnt -mabm -mbmi -mtbm -mfma4 -mxop -mlzcnt @gol @@ -12871,6 +12873,22 @@ Note that GCC implements 1.0f/sqrtf(x) in terms of RSQRTSS (or RSQRTPS) already with @option{-ffast-math} (or the above option combination), and doesn't need @option{-mrecip}. +@item -mrecip=@var{opt} +@opindex mrecip=opt +This option allows to control which reciprocal estimate instructions +may be used. @var{opt} is a comma separated list of options, that may +be preceded by a @code{!} to invert the option: +@code{all}: enable all estimate instructions, +@code{default}: enable the default instructions, equivalent to @option{-mrecip}, +@code{none}: disable all estimate instructions, equivalent to @option{-mno-recip}, +@code{div}: enable the approximation for scalar division, +@code{vec-div}: enable the approximation for vectorized division, +@code{sqrt}: enable the approximation for scalar square root, +@code{vec-sqrt}: enable the approximation for vectorized square root. + +So for example, @option{-mrecip=all,!sqrt} would enable +all of the reciprocal approximations, except for square root. + @item -mveclibabi=@var{type} @opindex mveclibabi Specifies the ABI type to use for vectorizing intrinsics using an |