public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug tree-optimization/103733] New: Missed optimization: defaulted op== for trivially comparable types worse than memcmp
@ 2021-12-15 11:49 jengelh at inai dot de
2021-12-15 12:37 ` [Bug tree-optimization/103733] " jakub at gcc dot gnu.org
` (5 more replies)
0 siblings, 6 replies; 7+ messages in thread
From: jengelh at inai dot de @ 2021-12-15 11:49 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=103733
Bug ID: 103733
Summary: Missed optimization: defaulted op== for trivially
comparable types worse than memcmp
Product: gcc
Version: 12.0
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: tree-optimization
Assignee: unassigned at gcc dot gnu.org
Reporter: jengelh at inai dot de
Target Milestone: ---
== Input ==
struct S {
char b[16];
#if __cplusplus >= 202000L
bool operator==(const S &) const = default;
#else
inline bool operator==(const S &o) const { return
__builtin_memcpy(const_cast<char *>(b), o.b, sizeof(b)); }
#endif
};
bool fff(const S &a, const S &b) { return a == b; }
== Observed ==
gcc version 12.0.0 20211214 973f6aedeb6489a9fdc7aeceaed0514348ee1e1a x86_64
$ ./xgcc -B. -c x.cpp -O2 -std=c++20 && objdump -d x.o
0000000000000000 <_Z3fffRK1SS1_>:
0: 31 c0 xor %eax,%eax
2: 66 0f 1f 44 00 00 nopw 0x0(%rax,%rax,1)
8: 0f b6 14 06 movzbl (%rsi,%rax,1),%edx
c: 38 14 07 cmp %dl,(%rdi,%rax,1)
f: 75 17 jne 28 <_Z3fffRK1SS1_+0x28>
11: 48 83 c0 01 add $0x1,%rax
15: 48 83 f8 10 cmp $0x10,%rax
19: 75 ed jne 8 <_Z3fffRK1SS1_+0x8>
1b: b8 01 00 00 00 mov $0x1,%eax
20: c3 ret
21: 0f 1f 80 00 00 00 00 nopl 0x0(%rax)
28: 31 c0 xor %eax,%eax
2a: c3 ret
== Expected ==
Expected the same result as when -std=c++17/memcmp is used.
0000000000000000 <_Z3fffRK1SS1_>:
0: f3 0f 6f 06 movdqu (%rsi),%xmm0
4: b8 01 00 00 00 mov $0x1,%eax
9: 0f 11 07 movups %xmm0,(%rdi)
c: c3 ret
^ permalink raw reply [flat|nested] 7+ messages in thread
* [Bug tree-optimization/103733] Missed optimization: defaulted op== for trivially comparable types worse than memcmp
2021-12-15 11:49 [Bug tree-optimization/103733] New: Missed optimization: defaulted op== for trivially comparable types worse than memcmp jengelh at inai dot de
@ 2021-12-15 12:37 ` jakub at gcc dot gnu.org
2021-12-15 13:38 ` jengelh at inai dot de
` (4 subsequent siblings)
5 siblings, 0 replies; 7+ messages in thread
From: jakub at gcc dot gnu.org @ 2021-12-15 12:37 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=103733
Jakub Jelinek <jakub at gcc dot gnu.org> changed:
What |Removed |Added
----------------------------------------------------------------------------
CC| |jakub at gcc dot gnu.org
--- Comment #1 from Jakub Jelinek <jakub at gcc dot gnu.org> ---
You are using memcpy instead of memcmp in your testcase, which does something
very different...
^ permalink raw reply [flat|nested] 7+ messages in thread
* [Bug tree-optimization/103733] Missed optimization: defaulted op== for trivially comparable types worse than memcmp
2021-12-15 11:49 [Bug tree-optimization/103733] New: Missed optimization: defaulted op== for trivially comparable types worse than memcmp jengelh at inai dot de
2021-12-15 12:37 ` [Bug tree-optimization/103733] " jakub at gcc dot gnu.org
@ 2021-12-15 13:38 ` jengelh at inai dot de
2021-12-15 13:50 ` jakub at gcc dot gnu.org
` (3 subsequent siblings)
5 siblings, 0 replies; 7+ messages in thread
From: jengelh at inai dot de @ 2021-12-15 13:38 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=103733
--- Comment #2 from Jan Engelhardt <jengelh at inai dot de> ---
== New input ==
$ cat x.cpp
struct S {
char b[16];
#if __cplusplus >= 202000L
bool operator==(const S &) const = default;
#else
inline bool operator==(const S &o) const { return __builtin_memcmp(b,
o.b, sizeof(b)); }
#endif
};
bool fff(const S &a, const S &b) { return a == b; }
== Observed ==
$ ./xgcc -B. -c /dev/shm/x.cpp -O2 && objdump -d x.o
0000000000000000 <_Z3fffRK1SS1_>: C++17
0: 48 8b 17 mov (%rdi),%rdx
3: 48 8b 47 08 mov 0x8(%rdi),%rax
7: 48 33 16 xor (%rsi),%rdx
a: 48 33 46 08 xor 0x8(%rsi),%rax
e: 48 09 d0 or %rdx,%rax
11: 0f 95 c0 setne %al
14: c3 ret
0000000000000000 <_Z3fffRK1SS1_>: C++20
0: 31 c0 xor %eax,%eax
2: 66 0f 1f 44 00 00 nopw 0x0(%rax,%rax,1)
8: 0f b6 14 06 movzbl (%rsi,%rax,1),%edx
c: 38 14 07 cmp %dl,(%rdi,%rax,1)
f: 75 17 jne 28 <_Z3fffRK1SS1_+0x28>
11: 48 83 c0 01 add $0x1,%rax
15: 48 83 f8 10 cmp $0x10,%rax
19: 75 ed jne 8 <_Z3fffRK1SS1_+0x8>
1b: b8 01 00 00 00 mov $0x1,%eax
20: c3 ret
21: 0f 1f 80 00 00 00 00 nopl 0x0(%rax)
28: 31 c0 xor %eax,%eax
2a: c3 ret
^ permalink raw reply [flat|nested] 7+ messages in thread
* [Bug tree-optimization/103733] Missed optimization: defaulted op== for trivially comparable types worse than memcmp
2021-12-15 11:49 [Bug tree-optimization/103733] New: Missed optimization: defaulted op== for trivially comparable types worse than memcmp jengelh at inai dot de
2021-12-15 12:37 ` [Bug tree-optimization/103733] " jakub at gcc dot gnu.org
2021-12-15 13:38 ` jengelh at inai dot de
@ 2021-12-15 13:50 ` jakub at gcc dot gnu.org
2021-12-16 13:44 ` jengelh at inai dot de
` (2 subsequent siblings)
5 siblings, 0 replies; 7+ messages in thread
From: jakub at gcc dot gnu.org @ 2021-12-15 13:50 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=103733
--- Comment #3 from Jakub Jelinek <jakub at gcc dot gnu.org> ---
That is still not equivalent, I bet you meant return !__builtin_memcmp.
Anyway, the reason we can optimize memcmp and can't optimize the loop that the
defaulted operator== emits is that there is no guarantee that all the bytes can
be safely accessed if there is a difference in the bytes before it.
Say when a points to end of mmaped region with only 8 bytes mapped in it and
similarly for b.
^ permalink raw reply [flat|nested] 7+ messages in thread
* [Bug tree-optimization/103733] Missed optimization: defaulted op== for trivially comparable types worse than memcmp
2021-12-15 11:49 [Bug tree-optimization/103733] New: Missed optimization: defaulted op== for trivially comparable types worse than memcmp jengelh at inai dot de
` (2 preceding siblings ...)
2021-12-15 13:50 ` jakub at gcc dot gnu.org
@ 2021-12-16 13:44 ` jengelh at inai dot de
2021-12-16 21:53 ` [Bug c++/103733] Defaulted operator== for arrays of integral types could be done using memcmp instead of loop pinskia at gcc dot gnu.org
2023-07-13 18:15 ` pinskia at gcc dot gnu.org
5 siblings, 0 replies; 7+ messages in thread
From: jengelh at inai dot de @ 2021-12-16 13:44 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=103733
--- Comment #4 from Jan Engelhardt <jengelh at inai dot de> ---
Is there a way to convey that it is safe to access every and all parts of S,
e.g. by initializing S::b at construction time?
^ permalink raw reply [flat|nested] 7+ messages in thread
* [Bug c++/103733] Defaulted operator== for arrays of integral types could be done using memcmp instead of loop
2021-12-15 11:49 [Bug tree-optimization/103733] New: Missed optimization: defaulted op== for trivially comparable types worse than memcmp jengelh at inai dot de
` (3 preceding siblings ...)
2021-12-16 13:44 ` jengelh at inai dot de
@ 2021-12-16 21:53 ` pinskia at gcc dot gnu.org
2023-07-13 18:15 ` pinskia at gcc dot gnu.org
5 siblings, 0 replies; 7+ messages in thread
From: pinskia at gcc dot gnu.org @ 2021-12-16 21:53 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=103733
Andrew Pinski <pinskia at gcc dot gnu.org> changed:
What |Removed |Added
----------------------------------------------------------------------------
Component|tree-optimization |c++
Keywords| |missed-optimization
Severity|normal |enhancement
Summary|Missed optimization: |Defaulted operator== for
|defaulted op== for |arrays of integral types
|trivially comparable types |could be done using memcmp
|worse than memcmp |instead of loop
^ permalink raw reply [flat|nested] 7+ messages in thread
* [Bug c++/103733] Defaulted operator== for arrays of integral types could be done using memcmp instead of loop
2021-12-15 11:49 [Bug tree-optimization/103733] New: Missed optimization: defaulted op== for trivially comparable types worse than memcmp jengelh at inai dot de
` (4 preceding siblings ...)
2021-12-16 21:53 ` [Bug c++/103733] Defaulted operator== for arrays of integral types could be done using memcmp instead of loop pinskia at gcc dot gnu.org
@ 2023-07-13 18:15 ` pinskia at gcc dot gnu.org
5 siblings, 0 replies; 7+ messages in thread
From: pinskia at gcc dot gnu.org @ 2023-07-13 18:15 UTC (permalink / raw)
To: gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=103733
Andrew Pinski <pinskia at gcc dot gnu.org> changed:
What |Removed |Added
----------------------------------------------------------------------------
Resolution|--- |DUPLICATE
Status|UNCONFIRMED |RESOLVED
--- Comment #5 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
Dup of bug 108953.
Even though PR 108953 is newer, it contains more details on how to fix this and
contains a few different/better testcases and such.
*** This bug has been marked as a duplicate of bug 108953 ***
^ permalink raw reply [flat|nested] 7+ messages in thread
end of thread, other threads:[~2023-07-13 18:15 UTC | newest]
Thread overview: 7+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-12-15 11:49 [Bug tree-optimization/103733] New: Missed optimization: defaulted op== for trivially comparable types worse than memcmp jengelh at inai dot de
2021-12-15 12:37 ` [Bug tree-optimization/103733] " jakub at gcc dot gnu.org
2021-12-15 13:38 ` jengelh at inai dot de
2021-12-15 13:50 ` jakub at gcc dot gnu.org
2021-12-16 13:44 ` jengelh at inai dot de
2021-12-16 21:53 ` [Bug c++/103733] Defaulted operator== for arrays of integral types could be done using memcmp instead of loop pinskia at gcc dot gnu.org
2023-07-13 18:15 ` 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).