public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug c/106138] New: Inefficient code generation for cases when results can be deduced at compile time
@ 2022-06-29 13:28 pavel.morozkin at gmail dot com
2022-06-29 14:27 ` [Bug tree-optimization/106138] " pinskia at gcc dot gnu.org
` (8 more replies)
0 siblings, 9 replies; 10+ messages in thread
From: pavel.morozkin at gmail dot com @ 2022-06-29 13:28 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106138
Bug ID: 106138
Summary: Inefficient code generation for cases when results can
be deduced at compile time
Product: gcc
Version: 12.1.0
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: c
Assignee: unassigned at gcc dot gnu.org
Reporter: pavel.morozkin at gmail dot com
Target Milestone: ---
_Bool f(char x)
{
_Bool b1 = x == 4;
_Bool b2 = x & 0x3;
return b1 && b2;
}
Invocation: gcc -O3
Actual generated code:
f:
test dil, 3
setne al
cmp dil, 4
sete dl
and eax, edx
ret
Expected generated code:
f:
xor eax, eax
ret
The Summary needs to be adjusted perhaps.
^ permalink raw reply [flat|nested] 10+ messages in thread
* [Bug tree-optimization/106138] Inefficient code generation for cases when results can be deduced at compile time
2022-06-29 13:28 [Bug c/106138] New: Inefficient code generation for cases when results can be deduced at compile time pavel.morozkin at gmail dot com
@ 2022-06-29 14:27 ` pinskia at gcc dot gnu.org
2022-06-30 7:26 ` rguenth at gcc dot gnu.org
` (7 subsequent siblings)
8 siblings, 0 replies; 10+ messages in thread
From: pinskia at gcc dot gnu.org @ 2022-06-29 14:27 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106138
Andrew Pinski <pinskia at gcc dot gnu.org> changed:
What |Removed |Added
----------------------------------------------------------------------------
Severity|normal |enhancement
^ permalink raw reply [flat|nested] 10+ messages in thread
* [Bug tree-optimization/106138] Inefficient code generation for cases when results can be deduced at compile time
2022-06-29 13:28 [Bug c/106138] New: Inefficient code generation for cases when results can be deduced at compile time pavel.morozkin at gmail dot com
2022-06-29 14:27 ` [Bug tree-optimization/106138] " pinskia at gcc dot gnu.org
@ 2022-06-30 7:26 ` rguenth at gcc dot gnu.org
2022-06-30 7:45 ` jakub at gcc dot gnu.org
` (6 subsequent siblings)
8 siblings, 0 replies; 10+ messages in thread
From: rguenth at gcc dot gnu.org @ 2022-06-30 7:26 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106138
Richard Biener <rguenth at gcc dot gnu.org> changed:
What |Removed |Added
----------------------------------------------------------------------------
CC| |amacleod at redhat dot com
--- Comment #1 from Richard Biener <rguenth at gcc dot gnu.org> ---
So we're seeing
b1_8 = x_7(D) == 4;
# RANGE [0, 3] NONZERO 3
_3 = x_7(D) & 3;
b2_9 = _3 != 0;
_5 = b1_8 & b2_9;
and fail to optimize that. It somewhat looks like "relations" (on x_7), but
I'm not sure if suitable to handle for ranger.
Adding something in match.pd might be possible - the key is of course that
both b1 and b2 are derived from the same value. I think we already have
a pattern looking at not intersecting nonzero bits.
^ permalink raw reply [flat|nested] 10+ messages in thread
* [Bug tree-optimization/106138] Inefficient code generation for cases when results can be deduced at compile time
2022-06-29 13:28 [Bug c/106138] New: Inefficient code generation for cases when results can be deduced at compile time pavel.morozkin at gmail dot com
2022-06-29 14:27 ` [Bug tree-optimization/106138] " pinskia at gcc dot gnu.org
2022-06-30 7:26 ` rguenth at gcc dot gnu.org
@ 2022-06-30 7:45 ` jakub at gcc dot gnu.org
2022-07-01 3:02 ` [Bug tree-optimization/106138] Inefficient code generation: logical AND of disjoint booleans from equal and bitwise AND not optimized to constant false peter at cordes dot ca
` (5 subsequent siblings)
8 siblings, 0 replies; 10+ messages in thread
From: jakub at gcc dot gnu.org @ 2022-06-30 7:45 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106138
Jakub Jelinek <jakub at gcc dot gnu.org> changed:
What |Removed |Added
----------------------------------------------------------------------------
CC| |jakub at gcc dot gnu.org
--- Comment #2 from Jakub Jelinek <jakub at gcc dot gnu.org> ---
I'd say reassoc would be a better place to handle it, so that we handle both
the logical op short circuit && and x == 4 && y == 25 && z != 16 && (x & 3) !=
0.
^ permalink raw reply [flat|nested] 10+ messages in thread
* [Bug tree-optimization/106138] Inefficient code generation: logical AND of disjoint booleans from equal and bitwise AND not optimized to constant false
2022-06-29 13:28 [Bug c/106138] New: Inefficient code generation for cases when results can be deduced at compile time pavel.morozkin at gmail dot com
` (2 preceding siblings ...)
2022-06-30 7:45 ` jakub at gcc dot gnu.org
@ 2022-07-01 3:02 ` peter at cordes dot ca
2022-07-04 14:47 ` amacleod at redhat dot com
` (4 subsequent siblings)
8 siblings, 0 replies; 10+ messages in thread
From: peter at cordes dot ca @ 2022-07-01 3:02 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106138
Peter Cordes <peter at cordes dot ca> changed:
What |Removed |Added
----------------------------------------------------------------------------
CC| |peter at cordes dot ca
--- Comment #3 from Peter Cordes <peter at cordes dot ca> ---
Ideally, bitwise & of booleans should also be handled, not just &&.
A testcase (https://godbolt.org/z/qvosv8q7c) makes it easy to check both.
//#define LOGIC_AND
_Bool f2(char x)
{
_Bool b1 = x == 2;
_Bool b2 = x & 1;
#ifdef LOGIC_AND
return b1 && b2;
#else
return b1 & b2;
#endif
}
(Clang optimized it to return false for the && version, but not bitwise. GCC
currently doesn't optimize either way.)
This was originally posted on Stack Overflow
(https://stackoverflow.com/q/72802469/224132), BTW.
^ permalink raw reply [flat|nested] 10+ messages in thread
* [Bug tree-optimization/106138] Inefficient code generation: logical AND of disjoint booleans from equal and bitwise AND not optimized to constant false
2022-06-29 13:28 [Bug c/106138] New: Inefficient code generation for cases when results can be deduced at compile time pavel.morozkin at gmail dot com
` (3 preceding siblings ...)
2022-07-01 3:02 ` [Bug tree-optimization/106138] Inefficient code generation: logical AND of disjoint booleans from equal and bitwise AND not optimized to constant false peter at cordes dot ca
@ 2022-07-04 14:47 ` amacleod at redhat dot com
2022-07-07 20:39 ` pinskia at gcc dot gnu.org
` (3 subsequent siblings)
8 siblings, 0 replies; 10+ messages in thread
From: amacleod at redhat dot com @ 2022-07-04 14:47 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106138
--- Comment #4 from Andrew Macleod <amacleod at redhat dot com> ---
(In reply to Richard Biener from comment #1)
> So we're seeing
>
> b1_8 = x_7(D) == 4;
> # RANGE [0, 3] NONZERO 3
> _3 = x_7(D) & 3;
> b2_9 = _3 != 0;
> _5 = b1_8 & b2_9;
>
> and fail to optimize that. It somewhat looks like "relations" (on x_7), but
> I'm not sure if suitable to handle for ranger.
>
> Adding something in match.pd might be possible - the key is of course that
> both b1 and b2 are derived from the same value. I think we already have
> a pattern looking at not intersecting nonzero bits.
Its not suitable yet anyway. theres an order of indirection in that any
relation is based on whether b1_8 and b2_9 are both 1 or both 0... If there
was a branch we start to pick up information on the edges... but without an
edge using _5, we don't yet try to paw back the same way.
perhaps we could optimize &/&& and |/|| to check if one of the operands doesnt
matter..
ie, if b1_8 is 1, then check if b2_9 is always 1 with the range of x_7([4,4]),
likewise if b1_8 is 0, then b2_9 doesnt matter. so we can simplify this to _5
= b1_8
it seems like something we could do with simplify_using_ranges quite easily by
utilizing gori perhaps? easy enough to pick up a range for b2_9 based on the
range of x_7 from b1_8 == [1,1]
^ permalink raw reply [flat|nested] 10+ messages in thread
* [Bug tree-optimization/106138] Inefficient code generation: logical AND of disjoint booleans from equal and bitwise AND not optimized to constant false
2022-06-29 13:28 [Bug c/106138] New: Inefficient code generation for cases when results can be deduced at compile time pavel.morozkin at gmail dot com
` (4 preceding siblings ...)
2022-07-04 14:47 ` amacleod at redhat dot com
@ 2022-07-07 20:39 ` pinskia at gcc dot gnu.org
2022-07-07 21:18 ` pinskia at gcc dot gnu.org
` (2 subsequent siblings)
8 siblings, 0 replies; 10+ messages in thread
From: pinskia at gcc dot gnu.org @ 2022-07-07 20:39 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106138
Andrew Pinski <pinskia at gcc dot gnu.org> changed:
What |Removed |Added
----------------------------------------------------------------------------
Ever confirmed|0 |1
Status|UNCONFIRMED |NEW
Last reconfirmed| |2022-07-07
--- Comment #5 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
(In reply to Jakub Jelinek from comment #2)
> I'd say reassoc would be a better place to handle it, so that we handle both
> the logical op short circuit && and x == 4 && y == 25 && z != 16 && (x & 3)
> != 0.
Right now reassoc calls maybe_fold_and_comparisons and
maybe_fold_or_comparisons which are places where this could be added. Or even
match-and-simplify gets called (via those two functions).
You could add it either in combine_comparisons or match.pd.
Maybe something like (psedu code as I didn't add the wi part and it can be
extended and all):
(simplify
(bit_and
(eq @0 INTEGER_CST@1)
(ne (bit_and @0 INTEGER_CST@2) zero_p))
(if ((@1 & @2) == 0))
({true_bool_value;}))
You can change @1 and @2 to
with_possible_nonzero_bits/with_possible_nonzero_bits2 and then compare the
nonzero bits to see if they overlap.
Also extend it to handle ior too.
^ permalink raw reply [flat|nested] 10+ messages in thread
* [Bug tree-optimization/106138] Inefficient code generation: logical AND of disjoint booleans from equal and bitwise AND not optimized to constant false
2022-06-29 13:28 [Bug c/106138] New: Inefficient code generation for cases when results can be deduced at compile time pavel.morozkin at gmail dot com
` (5 preceding siblings ...)
2022-07-07 20:39 ` pinskia at gcc dot gnu.org
@ 2022-07-07 21:18 ` pinskia at gcc dot gnu.org
2022-07-08 9:47 ` pavel.morozkin at gmail dot com
2022-07-08 19:35 ` pinskia at gcc dot gnu.org
8 siblings, 0 replies; 10+ messages in thread
From: pinskia at gcc dot gnu.org @ 2022-07-07 21:18 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106138
--- Comment #6 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
Note for:
bool f(char x)
{
bool b1 = x == 4;
bool b2 = x & 4;
return b1 && b2;
}
We should just get:
bool f(char x)
{
return x == 4;
}
bit_ior should be handled too.
^ permalink raw reply [flat|nested] 10+ messages in thread
* [Bug tree-optimization/106138] Inefficient code generation: logical AND of disjoint booleans from equal and bitwise AND not optimized to constant false
2022-06-29 13:28 [Bug c/106138] New: Inefficient code generation for cases when results can be deduced at compile time pavel.morozkin at gmail dot com
` (6 preceding siblings ...)
2022-07-07 21:18 ` pinskia at gcc dot gnu.org
@ 2022-07-08 9:47 ` pavel.morozkin at gmail dot com
2022-07-08 19:35 ` pinskia at gcc dot gnu.org
8 siblings, 0 replies; 10+ messages in thread
From: pavel.morozkin at gmail dot com @ 2022-07-08 9:47 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106138
--- Comment #7 from Pavel M <pavel.morozkin at gmail dot com> ---
May be useful: https://devblogs.microsoft.com/cppblog/new-code-optimizer.
Search for "Bit Estimator" section containing "Folding comparisons and
branches".
^ permalink raw reply [flat|nested] 10+ messages in thread
* [Bug tree-optimization/106138] Inefficient code generation: logical AND of disjoint booleans from equal and bitwise AND not optimized to constant false
2022-06-29 13:28 [Bug c/106138] New: Inefficient code generation for cases when results can be deduced at compile time pavel.morozkin at gmail dot com
` (7 preceding siblings ...)
2022-07-08 9:47 ` pavel.morozkin at gmail dot com
@ 2022-07-08 19:35 ` pinskia at gcc dot gnu.org
8 siblings, 0 replies; 10+ messages in thread
From: pinskia at gcc dot gnu.org @ 2022-07-08 19:35 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106138
--- Comment #8 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
(In reply to Pavel M from comment #7)
> May be useful: https://devblogs.microsoft.com/cppblog/new-code-optimizer.
> Search for "Bit Estimator" section containing "Folding comparisons and
> branches".
All of the infrastructure for the above referenced is already done really. This
is what with_possible_nonzero_bits/get_nonzero_bits is used for inside
match.pd. My original example match.pd used a constant but does not need to.
In fact GCC already handles:
bool f(int x)
{
if (x == 4)
if (x & 0x3)
return true;
return false;
}
It is the & case where GCC does not handle (&& in the original code is
converted into & early on as both sides do NOT have side effects and such).
^ permalink raw reply [flat|nested] 10+ messages in thread
end of thread, other threads:[~2022-07-08 19:35 UTC | newest]
Thread overview: 10+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-06-29 13:28 [Bug c/106138] New: Inefficient code generation for cases when results can be deduced at compile time pavel.morozkin at gmail dot com
2022-06-29 14:27 ` [Bug tree-optimization/106138] " pinskia at gcc dot gnu.org
2022-06-30 7:26 ` rguenth at gcc dot gnu.org
2022-06-30 7:45 ` jakub at gcc dot gnu.org
2022-07-01 3:02 ` [Bug tree-optimization/106138] Inefficient code generation: logical AND of disjoint booleans from equal and bitwise AND not optimized to constant false peter at cordes dot ca
2022-07-04 14:47 ` amacleod at redhat dot com
2022-07-07 20:39 ` pinskia at gcc dot gnu.org
2022-07-07 21:18 ` pinskia at gcc dot gnu.org
2022-07-08 9:47 ` pavel.morozkin at gmail dot com
2022-07-08 19:35 ` pinskia at gcc dot gnu.org
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).