This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
Re: [PATCH] handle bzero/bcopy in DSE and aliasing (PR 80933, 80934)
- From: Richard Biener <richard dot guenther at gmail dot com>
- To: Martin Sebor <msebor at gmail dot com>
- Cc: Gcc Patch List <gcc-patches at gcc dot gnu dot org>
- Date: Fri, 2 Jun 2017 13:12:41 +0200
- Subject: Re: [PATCH] handle bzero/bcopy in DSE and aliasing (PR 80933, 80934)
- Authentication-results: sourceware.org; auth=none
- References: <c10a89fa-e8cb-b2e5-ad02-be8a6d5e7a1f@gmail.com>
On Thu, Jun 1, 2017 at 10:52 PM, Martin Sebor <msebor@gmail.com> wrote:
> While testing some otherwise unrelated enhancements in these areas
> I noticed that calls to bzero and bcopy are not being handled as
> efficiently as equivalent calls to memset and memcpy. Specifically,
> redundant calls are not eliminated and the functions appear to be
> treated as if they allowed their pointer arguments to escape. This
> turned out to be due to the missing handling of the former two built
> ins by the DSE and aliasing passes.
>
> The attached patch adds this handling so the cases I noted in the two
> PRs are now handled.
+ /* The number of the size argument to one of the built-in functions
+ below. */
+ unsigned sizargno = 2;
/* Handle those builtin functions explicitly that do not act as
escape points. See tree-ssa-structalias.c:find_func_aliases
for the list of builtins we might need to handle here. */
@@ -2030,8 +2034,13 @@ call_may_clobber_ref_p_1 (gcall *call, ao_ref *ref)
&& gimple_call_builtin_p (call, BUILT_IN_NORMAL))
switch (DECL_FUNCTION_CODE (callee))
{
- /* All the following functions clobber memory pointed to by
- their first argument. */
+ case BUILT_IN_BZERO:
+ sizargno = 1;
+ /* Fall through. */
+
+ /* With the exception of the bzero function above, all of
+ the following clobber memory pointed to by their first
+ argument. */
case BUILT_IN_STRCPY:
case BUILT_IN_STRNCPY:
case BUILT_IN_MEMCPY:
@@ -2062,9 +2071,9 @@ call_may_clobber_ref_p_1 (gcall *call, ao_ref *ref)
is strlen (dest) + n + 1 instead of n, resp.
n + 1 at dest + strlen (dest), but strlen (dest) isn't
known. */
- if (gimple_call_num_args (call) == 3
+ if (gimple_call_num_args (call) > sizargno
&& DECL_FUNCTION_CODE (callee) != BUILT_IN_STRNCAT)
- size = gimple_call_arg (call, 2);
+ size = gimple_call_arg (call, sizargno);
ao_ref_init_from_ptr_and_size (&dref,
gimple_call_arg (call, 0),
size);
please insted do
if (DECL_FUNCTION_CODE (callee) == BUILT_IN_BZERO)
size = gimple_call_Arg (call, 1);
else if (gimple_call_num_args (call) == 3
...
instead of the above changes. Likewise in stmt_kills_ref_p.
Likewise in initialize_ao_ref_for_dse I see no value in uglifying the code
but instead do
case BUILT_IN_BCOPY:
{
ao_ref_init_from_ptr_and_size (write, gimple_call_arg (stmt,
1), gimple_call_arg (stmt, 2));
return true;
}
and similar for BZERO.
Similar in maybe_trim_memstar_call, for decrement_count simply pass in
the tree *
instead of the argno (and you can get rid of the stmt as well.
+ 1) Bzero and memset. */
+ bool memset_p = false;
if (is_gimple_reg_type (vr->type)
- && gimple_call_builtin_p (def_stmt, BUILT_IN_MEMSET)
- && integer_zerop (gimple_call_arg (def_stmt, 1))
- && tree_fits_uhwi_p (gimple_call_arg (def_stmt, 2))
+ && (((memset_p = gimple_call_builtin_p (def_stmt, BUILT_IN_MEMSET))
+ && integer_zerop (gimple_call_arg (def_stmt, 1))
+ && tree_fits_uhwi_p (gimple_call_arg (def_stmt, 2)))
+ || gimple_call_builtin_p (def_stmt, BUILT_IN_BZERO))
you miss the tree_fits_uhwi_p check for bzero.
Note I'd be _much_ more sympathetic to simply canonicalizing all of
bzero and bcopy
to memset / memmove and be done with all the above complexity.
Richard.
> Tested on x86_64-linux.
>
> Martin