C++ language linkage problem

Hi list!

In C++ standard (C++11) I can read the following about bsearch() library function (25.5.3 [alg.c.library]):

The function signature:
bsearch(const void *, const void *, size_t, size_t,
int (*)(const void *, const void *));

is replaced by the two declarations:

extern "C" void *bsearch(const void *key, const void *base,
size_t nmemb, size_t size,
int (*compar)(const void *, const void *));
extern "C++" void *bsearch(const void *key, const void *base,
size_t nmemb, size_t size,
int (*compar)(const void *, const void *));

But clang (3.4 from trunk) rejects to compile these 2 declarations:

$ cat a.cpp
typedef unsigned long size_t;

extern "C" void *bsearch(const void *key, const void *base,
         size_t nmemb, size_t size,
         int (*compar)(const void *, const void *));

extern "C++" void *bsearch(const void *key, const void *base,
         size_t nmemb, size_t size,
         int (*compar)(const void *, const void *));

$ ../build-clang-cmake/bin/clang++ -v -std=c++11 -c a.cpp
clang version 3.4
Target: i386-pc-solaris2.10
Thread model: posix
  "/export/home/sbn/src/build-clang-cmake/bin/clang-3.4" -cc1 -triple i386-pc-solaris2.10 -emit-obj -mrelax-all -disable-free -disable-llvm-verifier -main-file-name a.cpp -mrelocation-model static -mdisable-fp-elim -fmath-errno -masm-verbose -mconstructor-aliases -target-cpu pentium4 -v -coverage-file /export/home/sbn/src/extern-cpp/a.o -resource-dir /export/home/sbn/src/build-clang-cmake/bin/../lib/clang/3.4 -std=c++11 -fdeprecated-macro -fdebug-compilation-dir /export/home/sbn/src/extern-cpp -ferror-limit 19 -fmessage-length 237 -mstackrealign -fobjc-runtime=gcc -fobjc-default-synthesize-properties -fcxx-exceptions -fexceptions -fdiagnostics-show-option -fcolor-diagnostics -vectorize-loops -o a.o -x c++ a.cpp
clang -cc1 version 3.4 based upon LLVM 3.4svn default target i386-pc-solaris2.10
#include "..." search starts here:
#include <...> search starts here:
  /opt/csw/include/c++/4.8.0
  /opt/csw/include/c++/4.8.0/i386-pc-solaris2.10
  /opt/csw/include/c++/4.8.0/backward
  /export/home/sbn/src/build-clang-cmake/bin/../lib/clang/3.4/include
  /usr/include
End of search list.
a.cpp:7:20: error: declaration of 'bsearch' has a different language linkage
extern "C++" void *bsearch(const void *key, const void *base,
                    ^
a.cpp:3:18: note: previous declaration is here
extern "C" void *bsearch(const void *key, const void *base,
                  ^
1 error generated.

BTW this file is perfectly compile-able using clang 3.2:

$ /tb/soft/sun/x86_64/clang/bin/clang++ -v -std=c++11 -c a.cpp
clang version 3.2 (branches/release_32 174327)
Target: i386-pc-solaris2.10
Thread model: posix
  "/tb/soft/sun/i386/clang/bin/clang-3.2" -cc1 -triple i386-pc-solaris2.10 -emit-obj -mrelax-all -disable-free -disable-llvm-verifier -main-file-name a.cpp -mrelocation-model static -mdisable-fp-elim -fmath-errno -masm-verbose -mconstructor-aliases -target-cpu pentium4 -momit-leaf-frame-pointer -v -coverage-file /export/home/sbn/src/extern-cpp/a.o -resource-dir /tb/soft/sun/i386/clang/bin/../lib/clang/3.2 -fmodule-cache-path /var/tmp/clang-module-cache -std=c++11 -fdeprecated-macro -fdebug-compilation-dir /export/home/sbn/src/extern-cpp -ferror-limit 19 -fmessage-length 237 -mstackrealign -fobjc-runtime=gcc -fcxx-exceptions -fexceptions -fdiagnostics-show-option -fcolor-diagnostics -o a.o -x c++ a.cpp
clang -cc1 version 3.2 based upon LLVM 3.2svn default target i386-pc-solaris2.10
ignoring nonexistent directory "/opt/csw/include/c++/4.7.2"
ignoring nonexistent directory "/opt/csw/include/c++/4.7.2/i386-pc-solaris2.10/"
ignoring nonexistent directory "/opt/csw/include/c++/4.7.2/backward"
ignoring nonexistent directory "/tb/soft/sun/i386/clang/bin/../lib/clang/3.2/include"
#include "..." search starts here:
#include <...> search starts here:
  /usr/include
End of search list.

Is it some known bug/regression/fix or should I file a case?
Thanks!

The issue is that language linkage isn't part of a function type, and so the two functions appear to be declarations of the same function rather than overloads where one takes a pointer to a "C" linkage function and the other takes a pointer to a "C++" linkage function.

The reason this error is occurring now is that language linkage support is improving; clang can diagnose an error where a function is declared different times with different linkages, but support is not yet good enough to figure out that these two declarations are of different functions.

There's already a bug filed for this issue: http://llvm.org/bugs/show_bug.cgi?id=15563

Thanks for explanation!

These 2 bugs also seems related:
  - http://llvm.org/bugs/show_bug.cgi?id=6277
  - http://llvm.org/bugs/show_bug.cgi?id=12770