From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 48) id B47B53888163; Fri, 9 Dec 2022 21:17:34 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org B47B53888163 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gcc.gnu.org; s=default; t=1670620654; bh=xjmRTtFAbtTlyhss08hfDuHiJWIBwoDRcl99igiGHrM=; h=From:To:Subject:Date:From; b=Adt+FIcZet9VqwfyjLg5BDEWYtmoQCo1kgOvVPFn46qldGFuIOs2t/FqYtt/puE2u Pj/EwlpIJDK9lQtg4aYbHDwWpUfL31nxow0hrKU9+wm22Uq7uiNIUK34WLgl+RzBnk qOa/xQuchYoW/tg4F1fRXeOd6tGDcpz/HxS4w+wo= From: "law at gcc dot gnu.org" To: gcc-bugs@gcc.gnu.org Subject: [Bug target/108038] New: GCC generates poor code for select of consecutive constants Date: Fri, 09 Dec 2022 21:17:34 +0000 X-Bugzilla-Reason: CC X-Bugzilla-Type: new X-Bugzilla-Watch-Reason: None X-Bugzilla-Product: gcc X-Bugzilla-Component: target X-Bugzilla-Version: 13.0 X-Bugzilla-Keywords: X-Bugzilla-Severity: normal X-Bugzilla-Who: law at gcc dot gnu.org X-Bugzilla-Status: UNCONFIRMED X-Bugzilla-Resolution: X-Bugzilla-Priority: P3 X-Bugzilla-Assigned-To: unassigned at gcc dot gnu.org X-Bugzilla-Target-Milestone: --- X-Bugzilla-Flags: X-Bugzilla-Changed-Fields: bug_id short_desc product version bug_status bug_severity priority component assigned_to reporter cc target_milestone cf_gcctarget Message-ID: Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: quoted-printable X-Bugzilla-URL: http://gcc.gnu.org/bugzilla/ Auto-Submitted: auto-generated MIME-Version: 1.0 List-Id: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=3D108038 Bug ID: 108038 Summary: GCC generates poor code for select of consecutive constants Product: gcc Version: 13.0 Status: UNCONFIRMED Severity: normal Priority: P3 Component: target Assignee: unassigned at gcc dot gnu.org Reporter: law at gcc dot gnu.org CC: rzinsly at ventanamicro dot com Target Milestone: --- Target: riscv-64 This testcase: typedef signed long int __int64_t; #define X(OP, OPN) __int64_t test##OPN(__int64_t x, __int64_t y) { __int64_t cmp; cmp =3D (x OP y) ? 2 : 3; return cmp; } X(>,GT) X(<,LT) typedef unsigned long int __uint64_t; #define XU(OP, OPN) __uint64_t test##OPN(__uint64_t x, __uint64_t y) { __uint64_t cmp; cmp =3D (x OP y) ? 2 : 3; return cmp; } X(>,GTU) X(<,LTU) Compiled for rv64 with -O2 -march=3Drv64gc_zba gets this code for the first= test. The others are similar in having the extraneous xori.=20=20 testGT: sgt a0,a0,a1 # 25 [c=3D4 l=3D4] *sgt_didi xori a0,a0,1 # 27 [c=3D4 l=3D4] xordi3/1 addi a0,a0,2 # 16 [c=3D4 l=3D4] adddi3/1 ret # 35 [c=3D0 l=3D4] simple_return But ISTM we could generate this instead: testGT: sgt a0,a1,a0 # 24 [c=3D4 l=3D4] *riscv.md:2535 addi a0,a0,2 # 16 [c=3D4 l=3D4] adddi3/1 ret # 32 [c=3D0 l=3D4] simple_return I think the key is this: Trying 25 -> 27: 25: r139:DI=3Dr140:DI>r141:DI REG_DEAD r141:DI REG_DEAD r140:DI 27: r134:DI=3Dr139:DI^0x1 REG_DEAD r139:DI Failed to match this instruction: (set (reg:DI 134 [ ]) (le:DI (reg:DI 140) (reg:DI 141))) We can invert the condition and swap the operands with something like this: (define_insn "" [(set (match_operand:GPR 0 "register_operand" "=3Dr") (any_le:GPR (match_operand:X 1 "register_operand" " r") (match_operand:X 2 "register_operand" "r")))] "" "sgt\t%0,%2,%1" [(set_attr "type" "slt") (set_attr "mode" "")]) We probably need another pattern to handle the LT/LTU cases which want to match: rying 24 -> 25:=20 24: r139:DI=3Dr140:DI