[LLVMbugs] [Bug 18072] New: Template ambiguous operator overload - with tescase

bugzilla-daemon at llvm.org bugzilla-daemon at llvm.org
Tue Nov 26 16:10:33 PST 2013


http://llvm.org/bugs/show_bug.cgi?id=18072

            Bug ID: 18072
           Summary: Template ambiguous operator overload - with tescase
           Product: clang
           Version: trunk
          Hardware: PC
                OS: Linux
            Status: NEW
          Severity: normal
          Priority: P
         Component: C++
          Assignee: unassignedclangbugs at nondot.org
          Reporter: hal.ashburner at gmail.com
                CC: dgregor at apple.com, llvmbugs at cs.uiuc.edu
    Classification: Unclassified

clang++-3.4 exhibiting different behaviour to g++4.7 and clang++-3.3
Is it a bug? Is it a feature? 

Exception class with an overloaded output operator.
struct with an overloaded output operator.
Throw the exception using an overload to set its error message with the struct
in the message. The attached code should hopefully make it clear what is
intended.

It's some pretty deep template rules perhaps? Please do note the commented out
line in "do thing" that uses the same templates and compiles and runs as
expected. I can't see why the two invocations of the exception overload
operator should be treated differently but maybe there is deep
language-standardism that makes it all standards compliant and bug free(tm).
Anyway, thought you guys would like it boiled down to the smallest case I could
manage that you can just compile.
All the best.

Details:
most recent llvm-3.4 from here:
deb http://llvm.org/apt/raring/ llvm-toolchain-raring main
deb-src http://llvm.org/apt/raring/ llvm-toolchain-raring main

$ clang -v
Ubuntu clang version 3.4-1~exp1 (trunk) (based on LLVM 3.4)
Target: x86_64-pc-linux-gnu
Thread model: posix
Found candidate GCC installation: /usr/bin/../lib/gcc/x86_64-linux-gnu/4.6
Found candidate GCC installation: /usr/bin/../lib/gcc/x86_64-linux-gnu/4.6.4
Found candidate GCC installation: /usr/bin/../lib/gcc/x86_64-linux-gnu/4.7
Found candidate GCC installation: /usr/bin/../lib/gcc/x86_64-linux-gnu/4.7.3
Found candidate GCC installation: /usr/lib/gcc/x86_64-linux-gnu/4.6
Found candidate GCC installation: /usr/lib/gcc/x86_64-linux-gnu/4.6.4
Found candidate GCC installation: /usr/lib/gcc/x86_64-linux-gnu/4.7
Found candidate GCC installation: /usr/lib/gcc/x86_64-linux-gnu/4.7.3
Selected GCC installation: /usr/bin/../lib/gcc/x86_64-linux-gnu/4.7

compiler invocations:

$ clang++ -std=c++11 -Wall -g exception_op_overlad.cpp -o test-clang-3.4
$ g++ -std=c++11 -Wall -g exception_op_overlad.cpp -o test-g++4.7

compiler error seen:
clang++ -std=c++11 -Wall -g exception.cpp -o exception
exception.cpp:58:40: error: use of overloaded operator '<<' is ambiguous (with
      operand types 'exception' and 'thing_t')
     throw exception() << "some text " << th; // ok g++ 4.7, clang-3.3 f...
           ~~~~~~~~~~~~~~~~~~~~~~~~~~~ ^  ~~
exception.cpp:32:16: note: candidate function [with T = thing_t]
    exception& operator<<(T const& v)
               ^
exception.cpp:48:5: note: candidate function [with OS = exception]
OS& operator<<(OS& oss, const thing_t& t)
    ^
1 error generated.
make: *** [exception] Error 1


source:

#include <iostream>
#include <string>
#include <exception>
#include <sstream>

#define DUMP(x) std::cout << #x << " is " << x << std::endl

class exception : public std::exception
{
public:
    exception()
        : std::exception()
    {}

    exception(const exception &rhs)
        : std::exception(rhs)
    {
        errmsg.str(rhs.errmsg.str());
    }


    virtual ~exception() throw()
    {}

    virtual const char* what() const throw()
    {
        return errmsg.str().c_str();
    }


    template<typename T>
    exception& operator<<(T const& v)
    {
        this->errmsg << v;
        return *this;
    }

private:
    std::ostringstream errmsg;
};

struct thing_t
{
    int a;
};

template<typename OS>
OS& operator<<(OS& oss, const thing_t& t)
{
    oss << "thing is: " << t.a;
    return oss;
}


void do_thing(thing_t& th)
{
    // throw exception() << th; //ok all clang++-3.3 clag-3.4 g++4.7
     throw exception() << "some text " << th; // ok g++ 4.7, ok clang++-3.3
fails to compile on clang++-3.4
}

int main(int argc, char **argv)
{
    thing_t the_thing;
    the_thing.a = 8;

    try
    {
        do_thing(the_thing);
    }
    catch(exception& e)
    {
        std::cout << "e.what()" << " is " << e.what() << std::endl;
    }

}

-- 
You are receiving this mail because:
You are on the CC list for the bug.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/llvm-bugs/attachments/20131127/e7f73cad/attachment.html>


More information about the llvm-bugs mailing list