[cfe-dev] Issue with map and unordered_map: call to deleted constructor of 'std::pair<const int, int>'

Jeffrey Yasskin jyasskin at google.com
Sun Sep 18 00:59:55 PDT 2011


On Sat, Sep 17, 2011 at 11:09 PM, David Blaikie <dblaikie at gmail.com> wrote:
>
>
> On Sat, Sep 17, 2011 at 7:56 PM, David Blaikie <dblaikie at gmail.com> wrote:
>>>>
>>>> I was wondering if this is a bug in the gcc 4.5.2 standard library or a
>>>> bug in clang... and I'd really appreciate a work-around if anyone has one,
>>>> since I'm pretty much stuck at this point.
>>>
>>> As a baseline, this code compiles successfully when using libc++ (compile
>>> with -stdlib=libc++, though you'll of course need to install libc++) & I
>>> seem to have a repro of your errors with libstdc++ so I'm playing around
>>> with that now.
>>
>> I've investigated this a bit further with some help & I believe this is a
>> bug in clang ToT surrounding implicit move constructor/assignment.
>
> On further further investigation (& getting to what I think is the code
> that's generating this - and, helpfully, quotes the standard that supports
> it) I believe this is by design & libstdc++ has a bug.
> The relevant portion of the standard is 12.8[class.copy] paragraph 7:
>     ... If the class definition declares a move constructor or move
> assignment operator, the implicitly declared copy constructor
> is defined as deleted; otherwise, it is defined as defaulted. ...
> libstdc++'s std::pair should be defining the move/copy ctors/assignment
> operators (there's similar clauses for all these implicit definitions)
> explicitly if it wants to define the move assignment operator explicitly.

http://gcc.gnu.org/viewcvs?view=revision&revision=174464 changed some
things around here in May. Does it fix the bug you're looking at? It's
not in the gcc-4.6.x release branch, but we may be able to convince
them to include it in a future 4.6 release.

> [Miles: sorry about that, I'm checking your bug/repro now, but I'd hazard
> it's the same thing & a bug in boost rather than clang. I'll update when
> I've looked at it some more]
>
>>
>> Given this:
>>
>> struct foo {
>>   void operator=(foo&&);
>> };
>> int main() {
>>   foo g((foo()));
>> }
>>
>> Clang's output is:
>>
>>     simple.cc:6:7: error: call to deleted constructor of 'foo'
>>       foo g((foo()));
>>           ^ ~~~~~~~
>>     simple.cc:1:8: note: function has been explicitly marked deleted here
>>     struct foo {
>>            ^
>>
>> [g++ compiles this without error]
>> Clang seems to be implementing not providing implicit move operations by
>> implementing them as deleted rather than as not present. This would be
>> incorrect & produces the failure above.
>> The reason this came up in std::pair is a bit weird - it seems libstdc++'s
>> std::pair has none of the big 5 (copy ctor, move ctor, copy assignment, move
>> assignment, destructor) /except/ the move assignment operator. It does
>> however have member function templates that, while not technically copy/move
>> construction/assignment, are probably good enough for most cases. (returning
>> a temporary probably should invoke the copy ctor of libstdc++'s pair,
>> though, since it doesn't have a real move ctor which it should have)
>>
>> Anyway, the presence of the move assignment operator caused clang to
>> provide a deleted move ctor rather than no move ctor at all.
>> So there's the tale - I'll look into a fix & you'd be welcome to file a
>> bug (& assign it to me, though if someone else on the list really wants to
>> take it I don't mind), Matthieu. Thanks for bringing this up.
>> [side note: we should do a better job about the warning on "The Most
>> Vexing Parse" (see the declaration of 'g' in the above example which
>> required the extra () to be a variable declaration instead of a function
>> declaration) - like the parantheses warning I think we should have a couple
>> of notes suggesting the two ways to address the issue - most likely the user
>> actually meant to declare a variable & should insert the extra (). But
>> alternatively they can avoid the warning by removing the extra () after the
>> 'foo' in the argument list.]
>> - David
>>
>
>
> _______________________________________________
> cfe-dev mailing list
> cfe-dev at cs.uiuc.edu
> http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev
>
>




More information about the cfe-dev mailing list