[Bug d/101490] New: ICE at convert_expr(tree_node*, Type*, Type*)
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=101490 Bug ID: 101490 Summary: ICE at convert_expr(tree_node*, Type*, Type*) Product: gcc Version: 12.0 Status: UNCONFIRMED Severity: normal Priority: P3 Component: d Assignee: ibuclaw at gdcproject dot org Reporter: SztfG at yandex dot ru Target Milestone: --- testcase: import std.stdio; struct test { int[0] foo; }; void main() { test* t; auto a = cast(typeof((*t).foo)[0])t.foo; writeln(a); } /opt/wandbox/gdc-head/lib/gcc/x86_64-pc-linux-gnu/12.0.0/include/d/std/format.d: In function 'formatValue': /opt/wandbox/gdc-head/lib/gcc/x86_64-pc-linux-gnu/12.0.0/include/d/std/format.d:2605:23: internal compiler error: Floating point exception 2605 | formatValue(w, obj[], f); | ^ 0xc2df5f crash_signal ../../source/gcc/toplev.c:328 0x7b78c4 convert_expr(tree_node*, Type*, Type*) ../../source/gcc/d/d-convert.cc:476 0x7c9a5e ExprVisitor::visit(SliceExp*) ../../source/gcc/d/expr.cc:1382 0x7c74c0 build_expr(Expression*, bool, bool) ../../source/gcc/d/expr.cc:3129 0x7b60d1 d_build_call(TypeFunction*, tree_node*, tree_node*, Array*) ../../source/gcc/d/d-codegen.cc:2042 0x7c8f34 ExprVisitor::visit(CallExp*) ../../source/gcc/d/expr.cc:1886 0x7c74c0 build_expr(Expression*, bool, bool) ../../source/gcc/d/expr.cc:3129 0x7c755b build_expr_dtor(Expression*) ../../source/gcc/d/expr.cc:3152 0x7d3cf1 IRVisitor::visit(ExpStatement*) ../../source/gcc/d/toir.cc:1120 0x7d37bf IRVisitor::build_stmt(Statement*) ../../source/gcc/d/toir.cc:274 0x7d37bf IRVisitor::visit(CompoundStatement*) ../../source/gcc/d/toir.cc:1137 0x7d37bf IRVisitor::visit(CompoundStatement*) ../../source/gcc/d/toir.cc:1127 0x7d2e12 IRVisitor::build_stmt(Statement*) ../../source/gcc/d/toir.cc:274 0x7d2e12 build_function_body(FuncDeclaration*) ../../source/gcc/d/toir.cc:1549 0x7c6623 DeclVisitor::visit(FuncDeclaration*) ../../source/gcc/d/decl.cc:945 0x7c5b2f DeclVisitor::build_dsymbol(Dsymbol*) ../../source/gcc/d/decl.cc:146 0x7c5b2f DeclVisitor::visit(TemplateInstance*) ../../source/gcc/d/decl.cc:341 0x7c5b2f DeclVisitor::visit(TemplateInstance*) ../../source/gcc/d/decl.cc:332 0x7c31d6 DeclVisitor::build_dsymbol(Dsymbol*) ../../source/gcc/d/decl.cc:146 0x7c31d6 build_decl_tree(Dsymbol*) ../../source/gcc/d/decl.cc:986 Please submit a full bug report, with preprocessed source if appropriate. Please include the complete backtrace with any bug report. See <https://gcc.gnu.org/bugs/> for instructions.
[Bug d/101441] New: __FUNCTION__ doesn't work in core.stdc.stdio functions without cast
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=101441 Bug ID: 101441 Summary: __FUNCTION__ doesn't work in core.stdc.stdio functions without cast Product: gcc Version: 12.0 Status: UNCONFIRMED Severity: normal Priority: P3 Component: d Assignee: ibuclaw at gdcproject dot org Reporter: SztfG at yandex dot ru Target Milestone: --- testcase: import core.stdc.stdio; extern(C) int main(int argc, char **argv) { // works in ldc, dmd, doesnt work in gdc puts(__FUNCTION__); puts("test" ~ __FUNCTION__ ~ "test"); // works everywhere puts(cast(char*)__FUNCTION__); puts(cast(char*)("test " ~ __FUNCTION__ ~ "test")); return 0; }
[Bug d/101440] New: Documentation bug for __attribute__ ((access))
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=101440 Bug ID: 101440 Summary: Documentation bug for __attribute__ ((access)) Product: gcc Version: 10.1.0 URL: https://gcc.gnu.org/onlinedocs/gcc-10.1.0/gcc/Common-F unction-Attributes.html Status: UNCONFIRMED Keywords: documentation Severity: normal Priority: P3 Component: d Assignee: ibuclaw at gdcproject dot org Reporter: SztfG at yandex dot ru Target Milestone: --- >From documentation: > Examples of the use of the read_only access mode is the argument to the puts > function, or the second and third arguments to the memcpy function. > __attribute__ ((access (read_only, 1, 2))) void* memcpy (void*, const void*, > size_t); There is no reference to "third argument in memcpy function". Or I don't understand something? Maybe there must be __attribute__ ((access (write_only, 1, 3), access (read_only, 2, 3))) void* memcpy (void* restrict, const void* restrict, size_t); so, if we have void *memcpy(void *dest, const void *src, size_t n); then this function can write "size_t n" bytes to "void *dest" and read "size_t n" bytes from "void *src"
[Bug c/92487] New: case label error when label is made from character of C string
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=92487 Bug ID: 92487 Summary: case label error when label is made from character of C string Product: gcc Version: 9.2.1 Status: UNCONFIRMED Severity: normal Priority: P3 Component: c Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- testcase: void test(char x) { switch (x) { case "abc"[0]: // error: case label does not reduce to an integer constant printf("a\n"); break; case "abc"[1]: // error: case label does not reduce to an integer constant printf("b\n"); break; default: printf("other\n"); break; } } clang and icc is able to compile this. Clang with -pedantic telling > warning: expression is not an integer constant expression; folding it to a > constant is a GNU extension [-Wgnu-folding-constant] https://godbolt.org/z/xvGJB4 So this is some GNU extension, but why GCC doesn't support it?
[Bug tree-optimization/92233] New: missed optimisation for multiplication when it's known that at least one of the arguments is 0
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=92233 Bug ID: 92233 Summary: missed optimisation for multiplication when it's known that at least one of the arguments is 0 Product: gcc Version: 9.2.1 Status: UNCONFIRMED Keywords: missed-optimization Severity: normal Priority: P3 Component: tree-optimization Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- testcase: unsigned test_mult(unsigned a, unsigned b) { if ((a == 0) || (b == 0)) { return a*b; // here a*0 or 0*b or 0*0 - always 0 } return 0; } So this function should always return 0 no matter what, but GCC generate comparisons and imul instruction, even with -O3
[Bug tree-optimization/91882] boolean XOR tautology missed optimisation
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=91882 --- Comment #1 from SztfG at yandex dot ru --- Similar problem with other tautology: unsigned int impl_bit(unsigned int a, unsigned int b) // bitwise implication { return (~a | b); } unsigned int eq_bit(unsigned int a, unsigned int b) // bitwise equivalence { return (~a ^ b); } // good optimisation - "return 1;" unsigned int always_true(unsigned int a, unsigned int b) { return eq_bit(impl_bit(a,b), impl_bit(b,a)) == eq_bit(a, b); // ( (a -> b) = (b -> a) ) = (a = b) tautology } bool impl_bool(bool a, bool b { return (!a || b); } // bad optimisation bool always_true(bool a, bool b) { return (impl(a,b) == impl(b,a)) == (a == b); // ( (a -> b) = (b -> a) ) = (a = b) tautology }
[Bug tree-optimization/91882] New: boolean XOR tautology missed optimisation
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=91882 Bug ID: 91882 Summary: boolean XOR tautology missed optimisation Product: gcc Version: 10.0 Status: UNCONFIRMED Keywords: missed-optimization Severity: normal Priority: P3 Component: tree-optimization Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- This functions is always return true regardless of the value of the arguments: bool bool_xor_test(bool a, bool b) { return (a != b) == ((a || b) && !(a && b)); } bool bool_xor_test2(bool a, bool b) { return (a ^ b) == ((a || b) && !(a && b)); } but compiler does not simplify to "return true;". Expression ((a || b) && !(a && b)) poorly optimized BUT! In this case: bool xor_test_unsigned_int(unsigned int a, unsigned int b) { return (a ^ b) == ((a | b) & ~(a & b)); } It actually simlified to "return true;" : movl$1, %eax ret
[Bug tree-optimization/89478] missed optimization for lambda expression when variable is uninitialized when declared
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=89478 --- Comment #3 from SztfG at yandex dot ru --- Another testcase: int test4 = []() constexpr {int a = a; a = 5; return a;}(); GCC is able compile this, so it "think" this is valid constexpr lambda, but anyway doing this: _GLOBAL__sub_I_test4: movl$5, test4(%rip) ret test4: .zero 4
[Bug tree-optimization/89478] missed optimization for lambda expression when variable is uninitialized when declared
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=89478 --- Comment #2 from SztfG at yandex dot ru --- (In reply to Marc Glisse from comment #1) > I think the uninitialized variable makes the initialization not constexpr > (and indeed gcc/clang complain if you try to declare test constexpr). Then > we hit the well-known missed optimization that gcc is unable to convert a > dynamic initialization into a static initialization even in the most trivial > constant cases. Then need to mark this bug as duplicate, but where that bug in GCC bugzilla, which about that well-known missed optimization?
[Bug tree-optimization/89478] New: missed optimization for lambda expression when variable is uninitialized when declared
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=89478 Bug ID: 89478 Summary: missed optimization for lambda expression when variable is uninitialized when declared Product: gcc Version: 9.0 Status: UNCONFIRMED Keywords: missed-optimization Severity: normal Priority: P3 Component: tree-optimization Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- testcase: constexpr void mul2(int , const int b) { a = b * 2; } int test = []() {int a; mul2(a, 123); return a;}(); int test2 = []() {int a = 0; mul2(a, 123); return a;}(); output for GCC trunk with -O3 -std=c++17 _GLOBAL__sub_I_test: movl$246, test(%rip) ret test2: .long 246 test: .zero 4 simple testcase: int test3 = []() {int a; a = 5; return a;}(); _GLOBAL__sub_I_test: movl$5, test(%rip) ret test: .zero 4
[Bug tree-optimization/89360] New: GCC doesn't emit movcc instruction in some cases
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=89360 Bug ID: 89360 Summary: GCC doesn't emit movcc instruction in some cases Product: gcc Version: 9.0 Status: UNCONFIRMED Keywords: missed-optimization Severity: normal Priority: P3 Component: tree-optimization Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- Target: x86_64-linux-gnu Here are two function: void sort2_ternary(int a, int b, int *pa, int *pb) { *pa = a < b ? a : b; *pb = a < b ? b : a; } void sort2_if(int a, int b, int *pa, int *pb) { if (a < b) { *pa = a; *pb = b; } else { *pa = b; *pb = a; } } GCC does not emit CMOVcc (conditional move) on GCC 8.2 if we compile it as C++ code https://godbolt.org/z/ytE0Ix sort2_ternary(int, int, int*, int*): cmp edi, esi jge .L2 mov eax, edi mov edi, esi mov esi, eax .L2: mov DWORD PTR [rdx], esi mov DWORD PTR [rcx], edi ret sort2_if(int, int, int*, int*): cmp edi, esi jge .L5 mov DWORD PTR [rdx], edi mov DWORD PTR [rcx], esi ret .L5: mov DWORD PTR [rdx], esi mov DWORD PTR [rcx], edi ret but if compile it as C code, sort2_ternary have MOVcc: sort2_ternary: cmp esi, edi mov eax, edi cmovle eax, esi cmovl esi, edi mov DWORD PTR [rdx], eax mov DWORD PTR [rcx], esi ret but sort2_if remains same. On GCC trunk there is no difference between compiling this as C or C++ for sort2_ternary(), but sort2_if() still doesn't have CMOVcc instruction in it for both case. Measuring cmov vs branch-mov performance: https://github.com/xiadz/cmov
[Bug rtl-optimization/66152] suboptimal load bytes to stack
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66152 --- Comment #4 from SztfG at yandex dot ru --- GCC from trunk doing this: .Ltext0: .LC0: .string "" .ascii "\001\002\003\004\005\006\007" bar: .LFB0: sub rsp, 24 mov rax, QWORD PTR .LC0[rip] lea rdi, [rsp+8] mov QWORD PTR [rsp+8], rax call foo .LVL0: add rsp, 24 ret .LFE0: instead movabsq $506097522914230528, %rax
[Bug c/89157] New: Pointers comparison do not correspond to the standard
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=89157 Bug ID: 89157 Summary: Pointers comparison do not correspond to the standard Product: gcc Version: 9.0 Status: UNCONFIRMED Keywords: wrong-code Severity: normal Priority: P3 Component: c Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- Target: x86_64-linux-gnu Testcase: #include #include #include int main(void) { char a[8], b[8]; char *a_ptr = a+8; char *b_ptr = b; printf("a_ptr = %p, b_ptr = %p\n", a_ptr, b_ptr); if (a_ptr != b_ptr) { printf("a_ptr != b_ptr\n"); } else { printf("a_ptr == b_ptr\n"); } if ((uintptr_t)a_ptr != (uintptr_t)b_ptr) { printf("(uintptr_t)a_ptr != (uintptr_t)b_ptr\n"); } else { printf("(uintptr_t)a_ptr == (uintptr_t)b_ptr\n"); } return EXIT_SUCCESS; } Checked with option gcc test.c -std=c18 -Wall -Wextra -O2 Output: a_ptr = 0x7ffc0a1dea38, b_ptr = 0x7ffc0a1dea38 a_ptr != b_ptr (uintptr_t)a_ptr == (uintptr_t)b_ptr I think this is wrong. According to latest available C18 draft: https://web.archive.org/web/20181230041359if_/http://www.open-std.org/jtc1/sc22/wg14/www/abq/c17_updated_proposed_fdis.pdf#subsection.6.5.9 > Two pointers compare equal if and only if both are null pointers, both are > pointers to the same object(including a pointer to an object and a subobject > at its beginning) or function, both are pointers to one past the last element > of the same array object, or one is a pointer to one past the end of one > array object and the other is a pointer to the start of a different array > object that happens to immediately follow the first array object in the > address space. .111) > 111)Two objects may be adjacent in memory because they are adjacent elements > of a larger array or adjacent members of a structure with no padding between > them, or because the implementation chose to place them so, even though they > are unrelated. If prior invalid pointer operations (such as accesses outside > array bounds) produced undefined behavior, subsequent comparisons also > produce undefined behavior. Here we have the case when "one is a pointer to one past the end of one array object and the other is a pointer to the start of a different array object that happens to immediately follow the first array object in the address space" AND "implementation chose to place them so, even though they are unrelated".
[Bug tree-optimization/88603] New: optimization missed for saturation arithmetic add
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=88603 Bug ID: 88603 Summary: optimization missed for saturation arithmetic add Product: gcc Version: unknown Status: UNCONFIRMED Keywords: missed-optimization Severity: normal Priority: P3 Component: tree-optimization Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- Target: x86_64-linux-gnu example: #include uint32_t saturation_add(uint32_t a, uint32_t b) { const uint64_t tmp = (uint64_t)a + b; if (tmp > UINT32_MAX) { return UINT32_MAX; } return tmp; } output: mov edx, esi mov eax, edi add edi, esi # Why need to add two times here add rax, rdx # and here ? mov edx, 4294967295 cmp rax, rdx mov eax, -1 # Why? edx already have this value. -1 and 4294967295 are same cmovbe eax, edi ret better do something like this: add edi, esi mov eax, -1 cmovae eax, edi ret
[Bug c/87426] c_parser_unary_expression ICE
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=87426 --- Comment #1 from SztfG at yandex dot ru --- reduced testcase int arr[1] ={ 0 }; int test(int a) { return (arr[abs(a)]); }
[Bug c/87426] New: c_parser_unary_expression ICE
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=87426 Bug ID: 87426 Summary: c_parser_unary_expression ICE Product: gcc Version: 9.0 Status: UNCONFIRMED Severity: normal Priority: P3 Component: c Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- testcase: #include #include //#include static const uint32_t pow2[511] ={ 0 }; // doesnt matter #define SQR(x) pow2[x] uint16_t mul8b(uint8_t a, uint8_t b) { return (SQR((uint16_t)a+(uint16_t)b) - SQR(abs((int16_t)a-(int16_t)b))) >> 2;; } prog.c: In function 'mul8b': prog.c:12:46: warning: implicit declaration of function 'abs' [-Wimplicit-function-declaration] 12 | return (SQR((uint16_t)a+(uint16_t)b) - SQR(abs((int16_t)a-(int16_t)b))) >> 2;; | ^~~ prog.c:8:21: note: in definition of macro 'SQR' 8 | #define SQR(x) pow2[x] | ^ prog.c:12:3: internal compiler error: Segmentation fault 12 | return (SQR((uint16_t)a+(uint16_t)b) - SQR(abs((int16_t)a-(int16_t)b))) >> 2;; | ^~ 0xa31cbf crash_signal ../../source/gcc/toplev.c:325 0x5f8606 warn_for_abs ../../source/gcc/c/c-parser.c:9226 0x5f8606 c_parser_postfix_expression_after_primary ../../source/gcc/c/c-parser.c:9318 0x5ea523 c_parser_postfix_expression ../../source/gcc/c/c-parser.c:9006 0x5f2f27 c_parser_unary_expression ../../source/gcc/c/c-parser.c:7266 0x5f416f c_parser_cast_expression ../../source/gcc/c/c-parser.c:7110 0x5f43e6 c_parser_binary_expression ../../source/gcc/c/c-parser.c:6913 0x5f52f5 c_parser_conditional_expression ../../source/gcc/c/c-parser.c:6647 0x5f5830 c_parser_expr_no_commas ../../source/gcc/c/c-parser.c:6564 0x5f5a82 c_parser_expression ../../source/gcc/c/c-parser.c:9460 0x5f7fb7 c_parser_postfix_expression_after_primary ../../source/gcc/c/c-parser.c:9272 0x5ea523 c_parser_postfix_expression ../../source/gcc/c/c-parser.c:9006 0x5f2f27 c_parser_unary_expression ../../source/gcc/c/c-parser.c:7266 0x5f416f c_parser_cast_expression ../../source/gcc/c/c-parser.c:7110 0x5f4580 c_parser_binary_expression ../../source/gcc/c/c-parser.c:7036 0x5f52f5 c_parser_conditional_expression ../../source/gcc/c/c-parser.c:6647 0x5f5830 c_parser_expr_no_commas ../../source/gcc/c/c-parser.c:6564 0x5f5a82 c_parser_expression ../../source/gcc/c/c-parser.c:9460 0x5ea67b c_parser_postfix_expression ../../source/gcc/c/c-parser.c:7968 0x5f2f27 c_parser_unary_expression ../../source/gcc/c/c-parser.c:7266 Please submit a full bug report, with preprocessed source if appropriate. Please include the complete backtrace with any bug report. See <https://gcc.gnu.org/bugs/> for instructions.
[Bug c++/87208] dependent name resolution selects a function it should have NEVER considered
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=87208 --- Comment #2 from SztfG at yandex dot ru --- (In reply to Jonathan Wakely from comment #1) > Dup of PR 51577 ? Strictly speaking, it is not a dup, because PR 51577 and all the bugs marked as dups of PR 51577 are about finding an operator with namespaced parameters in the global namespace, but here the situation is the reverse. But the bugs could be closely related.
[Bug c++/87208] New: dependent name resolution selects a function it should have NEVER considered
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=87208 Bug ID: 87208 Summary: dependent name resolution selects a function it should have NEVER considered Product: gcc Version: unknown Status: UNCONFIRMED Severity: normal Priority: P3 Component: c++ Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- [temp.dep.res]/1: In resolving dependent names, names from the following sources are considered: — Declarations that are visible at the point of definition of the template. — Declarations from namespaces associated with the types of the function arguments both from the instantiation context and from the definition context. In the code below, g++ selects the free operator<<(), even though it is declared after the definition of the template and can't be found using ADL. #include struct S { template void operator<<(T) { std::printf("DEFAULT\n"); } }; namespace N { template void run(const T & value) { S s; s << value; } } struct MyValue {}; namespace N { void operator<<(S&, MyValue) { std::printf("OVERLOADED\n"); } } int main(int, char**) { N::run(MyValue()); } Expected output: DEFAULT Actual output: OVERLOADED
[Bug inline-asm/84625] New: ICE with constexpr and inline asm
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=84625 Bug ID: 84625 Summary: ICE with constexpr and inline asm Product: gcc Version: unknown Status: UNCONFIRMED Severity: normal Priority: P3 Component: inline-asm Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- testcase: #include void crasher() { constexpr __m128 w = {1,2,3,4}; asm ("addps %[w], %[w]" : : [w] ""(w)); }
[Bug c/51515] Unable to forward declare nested functions
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=51515 SztfG at yandex dot ru changed: What|Removed |Added CC||SztfG at yandex dot ru --- Comment #2 from SztfG at yandex dot ru --- but why this doesn't compile? void f() { typedef auto void (*func)(); func g(void); g(); func g() {} }
[Bug tree-optimization/80574] GCC fail to optimize nested ternary
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80574 SztfG at yandex dot ru changed: What|Removed |Added CC||SztfG at yandex dot ru --- Comment #6 from SztfG at yandex dot ru --- Created attachment 41316 --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=41316=edit some benchmark with macro stuff and std::max Well, maybe this is also not related to this issue, but here is some benchmark, and std::max is slower than macro
[Bug tree-optimization/80588] New: GCC can't simplify static inline function with xor/xnor
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80588 Bug ID: 80588 Summary: GCC can't simplify static inline function with xor/xnor Product: gcc Version: 7.0 Status: UNCONFIRMED Keywords: missed-optimization Severity: normal Priority: P3 Component: tree-optimization Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- GCC can't simplify static inline function for xor/xnor, but can, if used macro instead. Testcase: #include #define TYPE uint8_t #define M_XOR(a,b) ((!!(a))^(!!(b))) #define M_NXOR(a,b) (!((!!(a))^(!!(b __attribute__((__always_inline__, const)) static inline TYPE m_xor (const TYPE a, const TYPE b) { return M_XOR(a,b); } __attribute__((__always_inline__, const)) static inline TYPE m_xnor (const TYPE a, const TYPE b) { return M_NXOR(a,b); } // bad assembly output int test1b(const TYPE a, const TYPE b) { return m_xor(a,b) == !m_xnor(a,b); } int test2b(const TYPE a, const TYPE b) { return !m_xor(a,b) == m_xnor(a,b); } int test3b(const TYPE a, const TYPE b) { return M_XOR(a,b) == !m_xnor(a,b); } // good assembly output int test1g(const TYPE a, const TYPE b) { return m_xor(a,b) == M_XOR(a,b); } int test2g(const TYPE a, const TYPE b) { return M_XOR(a,b) == !M_NXOR(a,b); } int test3g(const TYPE a, const TYPE b) { return M_XOR(a,b) != !M_NXOR(a,b);; }
[Bug tree-optimization/80574] GCC fail to optimize nested ternary
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80574 --- Comment #5 from SztfG at yandex dot ru --- > He did not claim it was always better... Ahh, so I need to do some research to figure out, in which cases static inline function is better, and in which macro is better. It's bad > Please don't mix unrelated issues OK, will fill this in another bugreport
[Bug tree-optimization/80574] GCC fail to optimize nested ternary
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80574 --- Comment #3 from SztfG at yandex dot ru --- Georg-Johann Lay, GCC not always do things better if use static inline function instead macro. For example, this code: #include #define TYPE uint8_t #define M_XOR(a,b) ((!!a)^(!!b)) #define M_NXOR(a,b) (!((!!a)^(!!b))) __attribute__((__always_inline__, const)) static inline TYPE m_xor (const TYPE a, const TYPE b) { return M_XOR(a,b); } __attribute__((__always_inline__, const)) static inline TYPE m_xnor (const TYPE a, const TYPE b) { return M_NXOR(a,b); } // bad assembly output int test1b(const TYPE a, const TYPE b) { return m_xor(a,b) == !m_xnor(a,b); } int test2b(const TYPE a, const TYPE b) { return !m_xor(a,b) == m_xnor(a,b); } int test3b(const TYPE a, const TYPE b) { return M_XOR(a,b) == !m_xnor(a,b); } // good assembly output int test1g(const TYPE a, const TYPE b) { return m_xor(a,b) == M_XOR(a,b); } int test2g(const TYPE a, const TYPE b) { return M_XOR(a,b) == !M_NXOR(a,b); } int test3g(const TYPE a, const TYPE b) { return M_XOR(a,b) != !M_NXOR(a,b);; }
[Bug tree-optimization/80574] New: GCC fail to optimize nested ternary
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80574 Bug ID: 80574 Summary: GCC fail to optimize nested ternary Product: gcc Version: 7.0 Status: UNCONFIRMED Keywords: missed-optimization Severity: normal Priority: P3 Component: tree-optimization Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- Created attachment 41287 --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=41287=edit nested ternary sample GCC fail to optimize ternary chain (nested ternary) for find maximum value with unsigned types. Check attachment
[Bug tree-optimization/78383] New: label as values ICE with C++ lambda
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=78383 Bug ID: 78383 Summary: label as values ICE with C++ lambda Product: gcc Version: 7.0 Status: UNCONFIRMED Severity: normal Priority: P3 Component: tree-optimization Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- testcase: int main() { auto f = [](void* ptr) { goto *ptr; }; f(&); label: return 0; } $ g++ -std=c++11 -O2 test.cpp test.cpp: In function ‘main()::<lambda(void*)>’: test.cpp:3:23: internal compiler error: Segmentation fault auto f = [](void* ptr) { goto *ptr; }; ^
[Bug tree-optimization/71343] missed optimization (can't "prove" shift and multiplication equivalence)
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=71343 --- Comment #2 from SztfG at yandex dot ru --- This also not optimized by gcc: unsigned int test3(unsigned int a , unsigned int b) { return (a << 2) + (b << 2) == (a + b) << 2; } but this works: unsigned int test4(unsigned int a , unsigned int b) { return (a * 4) + (b * 4) == (a + b) * 4; } result: movl$1, %eax ret Distributive property also should work with binary shifts.
[Bug tree-optimization/71923] New: Two consecutive "rep ret" instruction in assembly output of recursive function
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=71923 Bug ID: 71923 Summary: Two consecutive "rep ret" instruction in assembly output of recursive function Product: gcc Version: 6.1.0 Status: UNCONFIRMED Keywords: missed-optimization Severity: normal Priority: P3 Component: tree-optimization Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- Host: x86_64-linux-gnu Target: x86_64-linux-gnu function unsigned int fact( unsigned int n) { return n < 1 ? 1 : n*fact(n-1); } produces fact: .LFB0: .cfi_startproc testl %edi, %edi movl$1, %eax je .L4 .p2align 4,,10 .p2align 3 .L3: imull %edi, %eax subl$1, %edi jne .L3 rep ret # <-- this instruction can be removed .L4: rep ret .cfi_endproc .LFE0: .size fact, .-fact .section.text.unlikely can be easily reproduced at http://gcc.godbolt.org/
[Bug rtl-optimization/71343] New: missed optimization (can't "prove" shift and multiplication equivalence)
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=71343 Bug ID: 71343 Summary: missed optimization (can't "prove" shift and multiplication equivalence) Product: gcc Version: 6.2.0 Status: UNCONFIRMED Keywords: missed-optimization Severity: normal Priority: P3 Component: rtl-optimization Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- this function unsigned int test12(unsigned int a , unsigned int b) { return ((a << 2) + (b << 2)) == a * 4 + b * 4; } cannot be reduced to "return 1;". Maybe here https://gcc.gnu.org/viewcvs/gcc/trunk/gcc/simplify-rtx.c?view=markup=232689#l2118 needs to add something? https://godbolt.org/g/vcEqe7 - here clang and ICC is able to reduce this, but not gcc
[Bug tree-optimization/68027] conditional statement and unnecessary register assignment
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68027 --- Comment #3 from SztfG at yandex dot ru --- btw why nobody confirm my old reported bug about stack-allocated array missed optimization https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66152 ?
[Bug tree-optimization/68027] conditional statement and unnecessary register assignment
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68027 --- Comment #4 from SztfG at yandex dot ru --- I think this can be optimized in this way: cmpl$100, %edi jg a1 jne a2 jmp a3 without any label jumps
[Bug middle-end/68027] conditional statement and unnecessary register assignment
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68027 --- Comment #1 from SztfG at yandex dot ru --- ># no need to do this, eax is equal $100 at this point I mean edi. after this part: cmpl$100, %edi jg .L5 jne .L6 if it passed this jg jne instruction without conditional jump, edi shoud be 100
[Bug middle-end/68027] New: conditional statement and unnecessary register assignment
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68027 Bug ID: 68027 Summary: conditional statement and unnecessary register assignment Product: gcc Version: unknown Status: UNCONFIRMED Severity: normal Priority: P3 Component: middle-end Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- C source code: int a1(int); int a2(int); int a3(int); int test1(int a) { if (a > 100) return a1(a); else if (a < 100) return a2(a); return a3(a); } --- Assembly output: test1: .LFB0: .cfi_startproc cmpl$100, %edi jg .L5 jne .L6 movl$100, %edi # no need to do this, eax is equal $100 at this point jmp a3 .p2align 4,,10 .p2align 3 .L6: jmp a2 .p2align 4,,10 .p2align 3 .L5: jmp a1 .cfi_endproc --- Tested on http://gcc.godbolt.org/ : gcc versions 4.4.7 - 5.2.0 have this problem.
[Bug tree-optimization/66178] Another label as values ICE
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66178 --- Comment #1 from SztfG at yandex dot ru --- better test case int test(void) { static int a = ((char *)l2-(char *)l3)+((char *)l1-(char *)l2); l1: l2: l3: return a; }
[Bug tree-optimization/66178] New: Another label as values ICE
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66178 Bug ID: 66178 Summary: Another label as values ICE Product: gcc Version: unknown Status: UNCONFIRMED Severity: normal Priority: P3 Component: tree-optimization Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- c and c++ compiler crashes. Testcase: void bar(int); int test(void) { static int test = ((char *)l2-(char *)l3)+((char *)l1-(char *)l2); l1: l2: l3: bar(test); return 0; }
[Bug tree-optimization/66178] Another label as values ICE
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66178 --- Comment #2 from SztfG at yandex dot ru --- another testcase: int test(void) { static int a = ((char *)l1-(char *)l2)-1; l1: l2: return a; }
[Bug tree-optimization/66123] [4.8/4.9/5 Regression] Array of labels as values + ternary operator + pointer arithmetic = internal compiler error
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66123 --- Comment #7 from SztfG at yandex dot ru --- Similar bug https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66178
[Bug rtl-optimization/66152] New: suboptimal load bytes to stack
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66152 Bug ID: 66152 Summary: suboptimal load bytes to stack Product: gcc Version: unknown Status: UNCONFIRMED Severity: normal Priority: P3 Component: rtl-optimization Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- for code void foo(char *); void bar(void) { char a[] = {0,1,2,3,4,5,6,7}; foo(a); } gcc generates many movb instructions: subq$24, %rsp movq%rsp, %rdi movb$0, (%rsp) movb$1, 1(%rsp) movb$2, 2(%rsp) movb$3, 3(%rsp) movb$4, 4(%rsp) movb$5, 5(%rsp) movb$6, 6(%rsp) movb$7, 7(%rsp) clang produces: pushq %rax movabsq $506097522914230528, %rax # imm = 0x706050403020100 movq%rax, (%rsp) leaq(%rsp), %rdi for 16-byte array, gcc 5.1.0 builds the array separately and copies it using movqda and movaps instruction i.e. : char a[] = {0,1,2,3,4,5,6,7,0,1,2,3,4,5,6,7}; produces: subq$24, %rsp movdqa .LC0(%rip), %xmm0 movq%rsp, %rdi movaps %xmm0, (%rsp) but if I make a 17-byte array, it again create movb instruction for each byte
[Bug rtl-optimization/66152] suboptimal load bytes to stack
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66152 --- Comment #1 from SztfG at yandex dot ru --- If array of char is initialized using string, gcc can use larger mov instruction, like movabsq, movq, movl etc. but not movdqa, movaps or other xmm But if zero byte appears in string, compiler always create a separate array and copy it to stack, using various mov instruction, except xmm-based void bar(void) { char a[4] = \x00\x02\x03\x04; foo(a); } produces .LC0: .string .string \002\003\004 bar: subq$24, %rsp movl.LC0(%rip), %eax movq%rsp, %rdi movl%eax, (%rsp) callfoo addq$24, %rsp ret
[Bug c/66123] New: Array of labels as values + ternary operator + pointer arithmetic = internal compiler error
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66123 Bug ID: 66123 Summary: Array of labels as values + ternary operator + pointer arithmetic = internal compiler error Product: gcc Version: unknown Status: UNCONFIRMED Severity: normal Priority: P3 Component: c Assignee: unassigned at gcc dot gnu.org Reporter: SztfG at yandex dot ru Target Milestone: --- Created attachment 35529 -- https://gcc.gnu.org/bugzilla/attachment.cgi?id=35529action=edit Preprocessed source bug.c: In function ‘test’: bug.c:1:5: internal compiler error: Segmentation fault Target: x86_64-linux-gnu gcc version 4.8.2 (Ubuntu 4.8.2-19ubuntu1) Code in attachment It also produces internal compiler error for ARM and ARM64 target