http://gcc.gnu.org/bugzilla/show_bug.cgi?id=56192
Bug #: 56192 Summary: global operator new() vs member operator new() Classification: Unclassified Product: gcc Version: 4.8.0 Status: UNCONFIRMED Severity: normal Priority: P3 Component: c++ AssignedTo: unassig...@gcc.gnu.org ReportedBy: ts...@mail.ru g++ 4.8.0 20130127 fails to compile the following code #include <cstddef> template <class> struct A {}; template <class T> A<decltype(new T)> f(int); template <class T> A<decltype(::new T)> g(int); struct X { void *operator new(std::size_t n, void *); }; int main() { using type = decltype(g<X>(0)); } ===================================================== Using built-in specs. COLLECT_GCC=bin/g++ COLLECT_LTO_WRAPPER=libexec/gcc/x86_64-linux-gnu/4.8.0/lto-wrapper Target: x86_64-linux-gnu Configured with: ../gcc-4.8-20130127/configure --prefix=/mnt/compiles/toolchains/cpp/4.8.0 --disable-nls --enable-languages=c,c++,go,fortran --enable-shared --enable-linker-build-id --with-system-zlib --without-included-gettext --enable-threads=posix --enable-clocale=gnu --enable-libstdcxx-time=yes --enable-gnu-unique-object --enable-plugin --enable-objc-gc --disable-werror --with-tune=generic --enable-checking=release --build=x86_64-linux-gnu --host=x86_64-linux-gnu --target=x86_64-linux-gnu --disable-bootstrap --disable-multilib --disable-shared --enable-static Thread model: posix gcc version 4.8.0 20130127 (experimental) (GCC) COLLECT_GCC_OPTIONS='-std=c++11' '-v' '-o' 'program' '-mtune=generic' '-march=x86-64' libexec/gcc/x86_64-linux-gnu/4.8.0/cc1plus -quiet -v -imultilib . -imultiarch x86_64-linux-gnu -D_GNU_SOURCE source.cpp -quiet -dumpbase source.cpp -mtune=generic -march=x86-64 -auxbase source -std=c++11 -version -o /tmp/ccKToF0B.s GNU C++ (GCC) version 4.8.0 20130127 (experimental) (x86_64-linux-gnu) compiled by GNU C version 4.7.2, GMP version 5.0.2, MPFR version 3.1.0-p3, MPC version 0.9 GGC heuristics: --param ggc-min-expand=100 --param ggc-min-heapsize=131072 ignoring nonexistent directory "/usr/local/include/x86_64-linux-gnu" ignoring nonexistent directory "lib/gcc/x86_64-linux-gnu/4.8.0/../../../../x86_64-linux-gnu/include" #include "..." search starts here: #include <...> search starts here: lib/gcc/x86_64-linux-gnu/4.8.0/../../../../include/c++/4.8.0 lib/gcc/x86_64-linux-gnu/4.8.0/../../../../include/c++/4.8.0/x86_64-linux-gnu/. lib/gcc/x86_64-linux-gnu/4.8.0/../../../../include/c++/4.8.0/backward lib/gcc/x86_64-linux-gnu/4.8.0/include /usr/local/include include lib/gcc/x86_64-linux-gnu/4.8.0/include-fixed x86_64-linux-gnu /usr/include End of search list. GNU C++ (GCC) version 4.8.0 20130127 (experimental) (x86_64-linux-gnu) compiled by GNU C version 4.7.2, GMP version 5.0.2, MPFR version 3.1.0-p3, MPC version 0.9 GGC heuristics: --param ggc-min-expand=100 --param ggc-min-heapsize=131072 Compiler executable checksum: c50b4a9e751f2a9ab933b25f6962a9bf source.cpp: In function 'int main()': source.cpp:19:33: error: no matching function for call to 'g(int)' using type = decltype(g<X>(0)); ^ source.cpp:19:33: note: candidate is: source.cpp:10:26: note: template<class T> A<decltype (new T)> g(int) A<decltype(::new T)> g(int); ^ source.cpp:10:26: note: template argument deduction/substitution failed: source.cpp: In substitution of 'template<class T> A<decltype (new T)> g(int) [with T = <missing>]': source.cpp:19:33: required from here source.cpp:10:26: error: no matching function for call to 'X::operator new(sizetype)' source.cpp:10:26: note: candidate is: source.cpp:14:11: note: static void* X::operator new(std::size_t, void*) void *operator new(std::size_t n, void *); ^ source.cpp:14:11: note: candidate expects 2 arguments, 1 provided source.cpp:19:33: error: no matching function for call to 'g(int)' using type = decltype(g<X>(0)); ^ source.cpp:19:33: note: candidate is: source.cpp:10:26: note: template<class T> A<decltype (new T)> g(int) A<decltype(::new T)> g(int); ^ source.cpp:10:26: note: template argument deduction/substitution failed: source.cpp: In substitution of 'template<class T> A<decltype (new T)> g(int) [with T = <missing>]': source.cpp:19:33: required from here source.cpp:10:26: error: no matching function for call to 'X::operator new(sizetype)' source.cpp:10:26: note: candidate is: source.cpp:14:11: note: static void* X::operator new(std::size_t, void*) void *operator new(std::size_t n, void *); ^ source.cpp:14:11: note: candidate expects 2 arguments, 1 provided ===================================================== The compiler ignores the presence of :: before new in the declaration of g and tries to find X::operator new() there. If we remove the declaration of f, the lookup for operator new() will be performed correctly. In my original code similar constructs are used as SFINAE triggers, so I can't just replace such decltype specifiers with well-known pointer types. See also examples in http://liveworkspace.org/code/3h5UIC$1 [You can switch between examples by means of the "changes" switcher]