From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 48) id 42A483858D3C; Thu, 25 Nov 2021 15:50:35 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org 42A483858D3C From: "ed at edwardrosten dot com" To: gcc-bugs@gcc.gnu.org Subject: [Bug tree-optimization/103429] Optimization of Auto-generated condition chain is not giving good lookup tables. Date: Thu, 25 Nov 2021 15:50:35 +0000 X-Bugzilla-Reason: CC X-Bugzilla-Type: changed X-Bugzilla-Watch-Reason: None X-Bugzilla-Product: gcc X-Bugzilla-Component: tree-optimization X-Bugzilla-Version: 12.0 X-Bugzilla-Keywords: missed-optimization X-Bugzilla-Severity: normal X-Bugzilla-Who: ed at edwardrosten dot com 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: Message-ID: In-Reply-To: References: 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 X-BeenThere: gcc-bugs@gcc.gnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Gcc-bugs mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Thu, 25 Nov 2021 15:50:35 -0000 https://gcc.gnu.org/bugzilla/show_bug.cgi?id=3D103429 --- Comment #2 from Edward Rosten --- It is doing if-to-switch, but only really with N=3D5, and only if force-inl= ine is set. I think this are two problems, one is that you need to force-inline in order to trigger if-to-switch. The other problem is that the if-to-switch conversion triggered only works = well for exactly 5 conditions, otherwise it uses a mix of converted and unconver= ted. It doesn't appear to be doing binary tree generation, more like linear sear= ch Here's the asm for N=3D7: run(int): ret run_inline(int): test edi, edi je .L13 cmp edi, 1 je .L14 cmp edi, 6 ja .L3 mov edi, edi jmp [QWORD PTR .L8[0+rdi*8]] .L8: .quad .L3 .quad .L3 .quad .L12 .quad .L11 .quad .L10 .quad .L9 .quad .L7 .L13: jmp void f<0>() .L7: jmp void f<6>() .L12: jmp void f<2>() .L11: jmp void f<3>() .L10: jmp void f<4>() .L9: jmp void f<5>() .L14: jmp void f<1>() .L3: ret Note, it's essentially doing: if(i=3D=3D0) f<0>(); else if(i=3D=3D1) f<1>(); else if(i > 6) return; else switch(i){ case 0: case 1:=20=20=20 return; case 2: f<2>(); return; case 3: f<3>(); return; case 4: f<4>(); return; case 5: f<5>(); return; case 6: f<6>(); return; } It's not doing binary searches. For, e.g. N%5 =3D=3D 1, the structure is mo= re like: if(i=3D=3D0) f<0>(); else if(i > 5){ if(i-5 > 4){ if(i-11>4){ if(i-16 > 4){=20 // and so on, linearly } else switch(i-16){ //... } } else switch(i-11){ //... } } else switch(i-6){ //... } } else switch(i){ case 0: return; case 1: f<1>(); return;=20=20 case 2: f<2>(); return; case 3: f<3>(); return; case 4: f<4>(); return; case 5: f<5>(); return; }=