From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mail-lf1-x12e.google.com (mail-lf1-x12e.google.com [IPv6:2a00:1450:4864:20::12e]) by sourceware.org (Postfix) with ESMTPS id 4155639B33D6 for ; Mon, 19 Dec 2022 09:26:46 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.1 sourceware.org 4155639B33D6 Authentication-Results: sourceware.org; dmarc=none (p=none dis=none) header.from=sifive.com Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=sifive.com Received: by mail-lf1-x12e.google.com with SMTP id c1so12749189lfi.7 for ; Mon, 19 Dec 2022 01:26:46 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=sifive.com; s=google; h=content-transfer-encoding:cc:to:subject:message-id:date:from :in-reply-to:references:mime-version:from:to:cc:subject:date :message-id:reply-to; bh=D8SdFCTulbpE6bT4Z++bqFYs+g0MDcRstVhMDc2atgo=; b=anO7jAXN17AxObSp8rzS1tP3TrXy3Y5yDsK9ND2+DsydqxRv9FdOaj3ypmjfATcCjw s1kxlRIB4MIl7VgVgiqrFg3puNBkzHPmRLbIGC1GTfr1LzeTD7deliCTE80oSDeIO1Ti Vz5Vwih0RNCDFurR+6mOAmREMtWN+hpEQzA/cOfMhUfJlkgKQNNCLbsKMBY1W1Srr7nB vBeLA01lTSdUFd5HriOrf3PrFW2b9u3tFykfgAsJ93D64r2NlAlLZTqNP0AzvltoZat3 nuR+RIaY4HyMCRu/gDYVFdK1Fb88Wo9K73gzMLvroReog5jWoQzBZ4iuCCB7JNqdumdM 7tMw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; h=content-transfer-encoding:cc:to:subject:message-id:date:from :in-reply-to:references:mime-version:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=D8SdFCTulbpE6bT4Z++bqFYs+g0MDcRstVhMDc2atgo=; b=m0O3faFUzRjooXlnjyQ96Bb6ewHOZW5w4qBlhIxjlIjQWyWr1Q5rZo4hifCX9PZRAB 5wWB8INzT5G0DQBGmGFAdYu0OeH8X9Y0HZ1ai3sG/9hxUH65jHC9mto9RZ9g80pxZX1L FWR75QF5RBhLwlkD3lynkbPOB2tOwsoli6TP2qHx87IE+NVLjHPlBcjQWi/WnGbot9zC OTruoAphuj/L4l0R8MA5ZQQBsYtxAp0K/kVGESoY3WsgbqWwUTljUemLiRdsYPdQyIgG 2rbZgj1sH/MVBgtHO2aglKAOZr8XQpUfprQaVg068DiywxM1FzFK7HnPyFcgzmta+kuF 61/Q== X-Gm-Message-State: ANoB5pl596MvTCsIBWfCZBWsVwcJbz8aphfpsBNwlsqXiBnzKsC5qz8l 3xeJ2kLCrC1g5TcpyQ9c8/LODOcIjm5fzW3rye69Ig== X-Google-Smtp-Source: AA0mqf6YpUsw1akgWP+gxY9T0xZ6YU8YcBrnO/traJXy4euPIGGE2gzN/xw7sRfFIvyTotL0H9JS+TflpcPxOjri0UQ= X-Received: by 2002:a05:6512:3762:b0:4ac:5faa:654d with SMTP id z2-20020a056512376200b004ac5faa654dmr30920873lft.684.1671442004721; Mon, 19 Dec 2022 01:26:44 -0800 (PST) MIME-Version: 1.0 References: <20221219010838.3878675-1-christoph.muellner@vrull.eu> <20221219010838.3878675-3-christoph.muellner@vrull.eu> In-Reply-To: From: Kito Cheng Date: Mon, 19 Dec 2022 17:26:33 +0800 Message-ID: Subject: Re: [PATCH v2 02/11] riscv: Restructure callee-saved register save/restore code To: =?UTF-8?Q?Christoph_M=C3=BCllner?= Cc: gcc-patches@gcc.gnu.org, Jim Wilson , Palmer Dabbelt , Andrew Waterman , Philipp Tomsich , Jeff Law , Cooper Qu , Lifang Xia , Yunhai Shang , Zhiwei Liu Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: quoted-printable X-Spam-Status: No, score=-9.6 required=5.0 tests=BAYES_00,DKIM_SIGNED,DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,GIT_PATCH_0,RCVD_IN_DNSWL_NONE,SPF_HELO_NONE,SPF_PASS,TXREP autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on server2.sourceware.org List-Id: Something like this: static unsigned int riscv_next_saved_reg (unsigned int regno, unsigned int limit, HOST_WIDE_INT *offset, bool inc =3D true) { if (inc) regno++; while (regno <=3D limit) { if (BITSET_P (cfun->machine->frame.mask, regno - GP_REG_FIRST)) { *offset =3D *offset - UNITS_PER_WORD; break; } regno++; } if (regno >=3D limit) return INVALID_REGNUM; else return regno; } ... for (regno =3D riscv_next_saved_reg (start, limit, &offset, false); regno !=3D INVALID_REGNUM; regno =3D riscv_next_saved_reg (regno, limit, &offset)) { ... On Mon, Dec 19, 2022 at 5:21 PM Christoph M=C3=BCllner wrote: > > > > On Mon, Dec 19, 2022 at 7:30 AM Kito Cheng wrote: >> >> just one more nit: Use INVALID_REGNUM as sentinel value for >> riscv_next_saved_reg, otherwise LGTM, and feel free to commit that >> separately :) > > > Would this change below be ok? > > @@ -5540,7 +5540,7 @@ riscv_next_saved_reg (unsigned int regno, unsigned = int limit, > if (inc) > regno++; > > - while (regno <=3D limit) > + while (regno <=3D limit && regno !=3D INVALID_REGNUM) > { > if (BITSET_P (cfun->machine->frame.mask, regno - GP_REG_FIRST)) > { > > Thanks, > Christoph > > >> >> >> On Mon, Dec 19, 2022 at 9:08 AM Christoph Muellner >> wrote: >> > >> > From: Christoph M=C3=BCllner >> > >> > This patch restructures the loop over the GP registers >> > which saves/restores then as part of the prologue/epilogue. >> > No functional change is intended by this patch, but it >> > offers the possibility to use load-pair/store-pair instructions. >> > >> > gcc/ChangeLog: >> > >> > * config/riscv/riscv.cc (riscv_next_saved_reg): New function. >> > (riscv_is_eh_return_data_register): New function. >> > (riscv_for_each_saved_reg): Restructure loop. >> > >> > Signed-off-by: Christoph M=C3=BCllner >> > --- >> > gcc/config/riscv/riscv.cc | 94 +++++++++++++++++++++++++++-----------= - >> > 1 file changed, 66 insertions(+), 28 deletions(-) >> > >> > diff --git a/gcc/config/riscv/riscv.cc b/gcc/config/riscv/riscv.cc >> > index 6dd2ab2d11e..a8d5e1dac7f 100644 >> > --- a/gcc/config/riscv/riscv.cc >> > +++ b/gcc/config/riscv/riscv.cc >> > @@ -4835,6 +4835,49 @@ riscv_save_restore_reg (machine_mode mode, int = regno, >> > fn (gen_rtx_REG (mode, regno), mem); >> > } >> > >> > +/* Return the next register up from REGNO up to LIMIT for the callee >> > + to save or restore. OFFSET will be adjusted accordingly. >> > + If INC is set, then REGNO will be incremented first. */ >> > + >> > +static unsigned int >> > +riscv_next_saved_reg (unsigned int regno, unsigned int limit, >> > + HOST_WIDE_INT *offset, bool inc =3D true) >> > +{ >> > + if (inc) >> > + regno++; >> > + >> > + while (regno <=3D limit) >> > + { >> > + if (BITSET_P (cfun->machine->frame.mask, regno - GP_REG_FIRST)) >> > + { >> > + *offset =3D *offset - UNITS_PER_WORD; >> > + break; >> > + } >> > + >> > + regno++; >> > + } >> > + return regno; >> > +} >> > + >> > +/* Return TRUE if provided REGNO is eh return data register. */ >> > + >> > +static bool >> > +riscv_is_eh_return_data_register (unsigned int regno) >> > +{ >> > + unsigned int i, regnum; >> > + >> > + if (!crtl->calls_eh_return) >> > + return false; >> > + >> > + for (i =3D 0; (regnum =3D EH_RETURN_DATA_REGNO (i)) !=3D INVALID_RE= GNUM; i++) >> > + if (regno =3D=3D regnum) >> > + { >> > + return true; >> > + } >> > + >> > + return false; >> > +} >> > + >> > /* Call FN for each register that is saved by the current function. >> > SP_OFFSET is the offset of the current stack pointer from the star= t >> > of the frame. */ >> > @@ -4844,36 +4887,31 @@ riscv_for_each_saved_reg (poly_int64 sp_offset= , riscv_save_restore_fn fn, >> > bool epilogue, bool maybe_eh_return) >> > { >> > HOST_WIDE_INT offset; >> > + unsigned int regno; >> > + unsigned int start =3D GP_REG_FIRST; >> > + unsigned int limit =3D GP_REG_LAST; >> > >> > /* Save the link register and s-registers. */ >> > - offset =3D (cfun->machine->frame.gp_sp_offset - sp_offset).to_const= ant (); >> > - for (unsigned int regno =3D GP_REG_FIRST; regno <=3D GP_REG_LAST; r= egno++) >> > - if (BITSET_P (cfun->machine->frame.mask, regno - GP_REG_FIRST)) >> > - { >> > - bool handle_reg =3D !cfun->machine->reg_is_wrapped_separately[= regno]; >> > - >> > - /* If this is a normal return in a function that calls the eh_= return >> > - builtin, then do not restore the eh return data registers a= s that >> > - would clobber the return value. But we do still need to sa= ve them >> > - in the prologue, and restore them for an exception return, = so we >> > - need special handling here. */ >> > - if (epilogue && !maybe_eh_return && crtl->calls_eh_return) >> > - { >> > - unsigned int i, regnum; >> > - >> > - for (i =3D 0; (regnum =3D EH_RETURN_DATA_REGNO (i)) !=3D I= NVALID_REGNUM; >> > - i++) >> > - if (regno =3D=3D regnum) >> > - { >> > - handle_reg =3D FALSE; >> > - break; >> > - } >> > - } >> > - >> > - if (handle_reg) >> > - riscv_save_restore_reg (word_mode, regno, offset, fn); >> > - offset -=3D UNITS_PER_WORD; >> > - } >> > + offset =3D (cfun->machine->frame.gp_sp_offset - sp_offset).to_const= ant () >> > + + UNITS_PER_WORD; >> > + for (regno =3D riscv_next_saved_reg (start, limit, &offset, false); >> > + regno <=3D limit; >> > + regno =3D riscv_next_saved_reg (regno, limit, &offset)) >> > + { >> > + if (cfun->machine->reg_is_wrapped_separately[regno]) >> > + continue; >> > + >> > + /* If this is a normal return in a function that calls the eh_r= eturn >> > + builtin, then do not restore the eh return data registers as = that >> > + would clobber the return value. But we do still need to save= them >> > + in the prologue, and restore them for an exception return, so= we >> > + need special handling here. */ >> > + if (epilogue && !maybe_eh_return >> > + && riscv_is_eh_return_data_register (regno)) >> > + continue; >> > + >> > + riscv_save_restore_reg (word_mode, regno, offset, fn); >> > + } >> > >> > /* This loop must iterate over the same space as its companion in >> > riscv_compute_frame_info. */ >> > -- >> > 2.38.1 >> >