On Wed, 2023-11-15 at 04:26 +0800, Xi Ruoyao wrote:
> On Tue, 2023-11-14 at 20:46 +0800, chenglulu wrote:
> >
> > 在 2023/11/14 下午5:55, Xi Ruoyao 写道:
> > > On Tue, 2023-11-14 at 17:45 +0800, Lulu Cheng wrote:
> > > > + /* When function calls are made through call36, t0 register
> > > > will be
> > > > + implicitly modified, so '-fno-ipa-ra' needs to be set
> > > > here. */
> > > > case CMODEL_MEDIUM:
> > > > + if (HAVE_AS_SUPPORT_CALL36)
> > > > + opts->x_flag_ipa_ra = 0;
> > > > + break;
> > > Maybe we can add a (clobber (reg:P 12)) to the related insns
> > > instead?
> > >
> > Sorry, this was modified in accordance with the call36 macro
> > instruction
> > during the test.
> > I will use clobber, and add test cases.
>
> There seems a better solution as suggested by the GCC internal doc.
> Section 18.9.16 mentions -fipa-ra:
>
> -- Target Hook: bool TARGET_CALL_FUSAGE_CONTAINS_NON_CALLEE_CLOBBERS
> Set to true if each call that binds to a local definition
> explicitly clobbers or sets all non-fixed registers modified by
> performing the call. That is, by the call pattern itself, or by
> code that might be inserted by the linker (e.g. stubs, veneers,
> branch islands), but not including those modifiable by the callee.
> The affected registers may be mentioned explicitly in the call
> pattern, or included as clobbers in CALL_INSN_FUNCTION_USAGE. The
> default version of this hook is set to false. The purpose of this
> hook is to enable the fipa-ra optimization.
>
> So we can add t0 into CALL_INSN_FUNCTION_USAGE of the call insn, like:
>
> diff --git a/gcc/config/loongarch/loongarch.md
> b/gcc/config/loongarch/loongarch.md
> index ea36542b1c3..96e7e98e6b3 100644
> --- a/gcc/config/loongarch/loongarch.md
> +++ b/gcc/config/loongarch/loongarch.md
> @@ -3274,7 +3274,14 @@ (define_expand "sibcall"
> XEXP (target, 1),
> operands[1]));
> else
> - emit_call_insn (gen_sibcall_internal (target, operands[1]));
> + {
> + rtx call = gen_sibcall_internal (target, operands[1]);
> +
> + if (TARGET_CMODEL_MEDIUM && !REG_P (target))
> + clobber_reg (&CALL_INSN_FUNCTION_USAGE (call),
> + gen_rtx_REG (Pmode, T0_REGNUM));
> + emit_call_insn (call);
> + }
> DONE;
> })
>
> Likewise for sibcall_value.
Nope. This does not work for
__attribute__((noinline)) void q() { asm ("":::"memory"); }
__attribute__((noinline)) static void t() { q(); }
int
main ()
{
int x0 = 114514;
asm("":"+r"(x0));
t();
if (x0 != 114514)
__builtin_trap ();
}
Not sure why...
>
> By the way we'd better have a command line switch to override the build-
> time check for assembler call36 support, because it makes writing test
> cases and inter-operating with different versions of assembler easier.
>
--
Xi Ruoyao <[email protected]>
School of Aerospace Science and Technology, Xidian University