This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
Re: Improve ECF_NOTHROW flags for direct internal functions
- From: Richard Biener <richard dot guenther at gmail dot com>
- To: GCC Patches <gcc-patches at gcc dot gnu dot org>, Richard Sandiford <richard dot sandiford at linaro dot org>
- Date: Thu, 17 Aug 2017 12:29:42 +0200
- Subject: Re: Improve ECF_NOTHROW flags for direct internal functions
- Authentication-results: sourceware.org; auth=none
- References: <87k222frr1.fsf@linaro.org>
On Thu, Aug 17, 2017 at 11:49 AM, Richard Sandiford
<richard.sandiford@linaro.org> wrote:
> Internal functions that map directly to an optab can only throw an
> exception for -fnon-call-exceptions. This patch handles that in
> internal_fn_flags, in a similar way to ATTR_*NOTHROW in builtins.def.
>
> (Functions that don't throw even for flag_non_call_exceptions should be
> explicitly marked ECF_NOTHROW in internal-fn.def.)
>
> Tested on aarch64-linux-gnu and x86_64-linux-gnu. OK to install?
Hmm. Note the outcome of flag_non_call_exceptions depends on the
current function and thus IPA passes querying flags would need to
push an appropriate function context. This means the function should
get a struct function * argument and opt_for_fn (fn, flag_non_call_exceptions)
should be used. It doesn't help very much that all callers don't have
any such context either which means this "optimization" looks like
in the wrong place :/ (the global value of flag_non_call_exceptions in
the IPA case isn't necessarily conservative).
So if you insist then add a comment and add a && cfun check so
we're sure we are in non-IPA context (or in properly setup context).
Richard.
> Richard
>
>
> 2017-08-17 Richard Sandiford <richard.sandiford@linaro.org>
>
> gcc/
> * internal-fn.h (internal_fn_flags): Just declare and move
> the actual implementation out-of-line to...
> * internal-fn.c (internal_fn_flags): ...here. Set ECF_NOTHROW for
> directly-mapped internal functions if !flag_non_call_exceptions.
>
> Index: gcc/internal-fn.h
> ===================================================================
> --- gcc/internal-fn.h 2017-02-23 19:54:03.000000000 +0000
> +++ gcc/internal-fn.h 2017-08-17 09:05:37.459968561 +0100
> @@ -107,15 +107,7 @@ internal_fn_name (enum internal_fn fn)
> return internal_fn_name_array[(int) fn];
> }
>
> -/* Return the ECF_* flags for function FN. */
> -
> -extern const int internal_fn_flags_array[];
> -
> -static inline int
> -internal_fn_flags (enum internal_fn fn)
> -{
> - return internal_fn_flags_array[(int) fn];
> -}
> +extern int internal_fn_flags (enum internal_fn fn);
>
> /* Return fnspec for function FN. */
>
> Index: gcc/internal-fn.c
> ===================================================================
> --- gcc/internal-fn.c 2017-08-10 14:36:07.453493083 +0100
> +++ gcc/internal-fn.c 2017-08-17 09:05:37.459968561 +0100
> @@ -2814,3 +2814,18 @@ expand_PHI (internal_fn, gcall *)
> {
> gcc_unreachable ();
> }
> +
> +/* Return the ECF_* flags for function FN. */
> +
> +int
> +internal_fn_flags (enum internal_fn fn)
> +{
> + int flags = internal_fn_flags_array[(int) fn];
> + /* Functions that map to optabs can only throw a catchable exception
> + when non-call exceptions are enabled. The non-call exceptions in
> + these cases will typically come from things like IEEE exceptions,
> + divide by zero errors and SEGVs. */
> + if (direct_internal_fn_p (fn) && !flag_non_call_exceptions)
> + flags |= ECF_NOTHROW;
> + return flags;
> +}