https://gcc.gnu.org/bugzilla/show_bug.cgi?id=115621
Bug ID: 115621 Summary: internal compiler error: Segmentation fault with ambiguous operator Product: gcc Version: 14.1.1 Status: UNCONFIRMED Severity: normal Priority: P3 Component: c++ Assignee: unassigned at gcc dot gnu.org Reporter: jan.zizka at nokia dot com Target Milestone: --- Created attachment 58507 --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=58507&action=edit Reproducer preprocessed source When compiling below code with gcc 14.1.1 (in Fedora 40) an internal error is thrown. The same compiles with gcc 13.3.1 (in Fedora 39). $ g++ -freport-bug reproduce.cpp -c -o reproduce.o reproduce.cpp: In function ‘void test()’: reproduce.cpp:68:38: internal compiler error: Segmentation fault 68 | log::print<int>() << "data: " << master_data; | ^~~~~~~~~~~ Please submit a full bug report, with preprocessed source. See <http://bugzilla.redhat.com/bugzilla> for instructions. Preprocessed source stored into /tmp/ccCeduvz.out file, please attach this to your bugreport. #include <cstdlib> #include <stddef.h> #include <cstring> #include <stddef.h> class data_class { public: inline const int& operator*() const { return data; } private: int data; }; class data_stream { public: data_stream& operator<<(char c) { return *this; } }; inline data_stream& operator<<(data_stream& out, const data_class& value) { return out << *value; } class text_stream { public: template <typename T> text_stream& operator<<(T val) { return *this; } }; inline text_stream& operator<<(text_stream& out, const data_class& value) { return out << *value; } template <class Level, class Component> class log_stream_aa { public: template <typename T> log_stream_aa& operator<<(const T& t) { return *this; } }; template <class Level, class Component> struct log_config { typedef log_stream_aa<Level, Component> stream; }; template <class Component> class basic_log { public: template <class Level> class print : public log_config<Level, Component>::stream { public: print() : log_config<Level, Component>::stream() { } }; }; typedef basic_log<int> log; typedef unsigned char data_type[8]; const data_type master_data = {0x5, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0}; template <typename Stream> inline Stream& operator<<(Stream& stream, const data_type& value) { return stream; } void test() { log::print<int>() << "data: " << master_data; } The code was reduced from rather large code base. I assume the problem is triggered while diagnostics tries to warn about ambiguous operator<<. The legacy code is not proper but the compiler should not issue ICE. When template <typename Stream> inline Stream& operator<<(Stream& stream, const data_type& value) { return stream; } is removed the code compiles without ICE. When compiling with clang 18.1.1 following error is reported: $ clang reproduce.cpp -c -o reproduce.o reproduce.cpp:68:35: error: use of overloaded operator '<<' is ambiguous (with operand types 'log_stream_aa<int, int>' and 'const data_type' (aka 'const unsigned char[8]')) 68 | log::print<int>() << "data: " << master_data; | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ^ ~~~~~~~~~~~ reproduce.cpp:36:20: note: candidate function [with T = unsigned char[8]] 36 | log_stream_aa& operator<<(const T& t) { return *this; } | ^ reproduce.cpp:64:16: note: candidate function [with Stream = log_stream_aa<int, int>] 64 | inline Stream& operator<<(Stream& stream, const data_type& value) { return stream; } | ^ 1 error generated. I believe that gcc is trying to report same problem during which it crashes.