On Sun, Jun 29, 2025, 12:18 PM Jeff Law <jeffreya...@gmail.com> wrote:
> > > On 6/27/25 12:16 AM, Andrew Pinski wrote: > > Since after a tail call function (even if it is tail called in the end), > > the current function does not care about the local memory any more so > > there is no reason to do a copy of the argument. This is only true for > the > > first usage of the decl, the rest requires a copy > (c-c++-common/pr42909-3.c checks that). > > > > Bootstrapped and tested on aarch64-linux-gnu. > > > > PR middle-end/42909 > > gcc/ChangeLog: > > > > * calls.cc (initialize_argument_information): For tail > > calls allow to reuse the argument if it is not addressable > > nor static if the first use of the decl. Disallow tails if > > that argument is not an incoming argument. > > > > gcc/testsuite/ChangeLog: > > > > * c-c++-common/pr42909-1.c: New testcase > > * c-c++-common/pr42909-2.c: New testcase > > * c-c++-common/pr42909-3.c: New testcase > > * c-c++-common/pr42909-4.c: New testcase > > > > Signed-off-by: Andrew Pinski <quic_apin...@quicinc.com> > > --- > > gcc/calls.cc | 33 ++++++++++++++++++---- > > gcc/testsuite/c-c++-common/pr42909-1.c | 19 +++++++++++++ > > gcc/testsuite/c-c++-common/pr42909-2.c | 19 +++++++++++++ > > gcc/testsuite/c-c++-common/pr42909-3.c | 38 ++++++++++++++++++++++++++ > > gcc/testsuite/c-c++-common/pr42909-4.c | 20 ++++++++++++++ > > 5 files changed, 124 insertions(+), 5 deletions(-) > > create mode 100644 gcc/testsuite/c-c++-common/pr42909-1.c > > create mode 100644 gcc/testsuite/c-c++-common/pr42909-2.c > > create mode 100644 gcc/testsuite/c-c++-common/pr42909-3.c > > create mode 100644 gcc/testsuite/c-c++-common/pr42909-4.c > > > > > @@ -1428,15 +1430,37 @@ initialize_argument_information (int num_actuals > ATTRIBUTE_UNUSED, > > const bool callee_copies > > = reference_callee_copied (args_so_far_pnt, arg); > > tree base; > > - > > + bool can_reuse_arg = false; > > + bool can_reuse_with_tail_call = call_from_thunk_p; > > /* If we're compiling a thunk, pass directly the address of an > object > > already in memory, instead of making a copy. Likewise if we > want > > - to make the copy in the callee instead of the caller. */ > > + to make the copy in the callee instead of the caller. */ > Whitespace nit at the comment close. Guessing you didn't mean to make > that change. > Yes i think the patch i was originally going to do was touch this if statement but decided it was going to be too complex and I didn't revert all of the changes it seems. > > > if ((call_from_thunk_p || callee_copies) > > && TREE_CODE (args[i].tree_value) != WITH_SIZE_EXPR > > && ((base = get_base_address (args[i].tree_value)), true) > > && TREE_CODE (base) != SSA_NAME > > && (!DECL_P (base) || MEM_P (DECL_RTL (base)))) > > + can_reuse_arg = true; > > + > > + /* If we're compiling a tail call, pass the address of an object > > + already in memory, instead of a copy if the argument is a > local > > + variable. Since after the tail call, the memory belongs to > the caller, > > + this is safe even if we don't expand the call in the end as a > tail call. > > + The first use of the decl can reuse it, the rest uses > requires a copy. */ > What about a set before any use? Does everything still work in that case? > Let me clarify the first use here means, it should be first use as an argument to this call. And yes setting part of it before the statement works too. I will add some more testcases to show that doing setting part of it before hand is correct. > Assuming the right things happen if there's an assignment to the > argument before the first use, then this is OK. Otherwise I think you > need more changes. > It does work correct. I will clarify the comment and add a few more testcases and submit again (most likely tomorrow as I am traveling today). Thanks, Andrew > jeff > > > >