[operators] moving forward use return by reference for compilers with proper support?
Following some feedback I got from MS about the disparity between VS2012 and GCC/Clang in how some the lifetimes of temporaries are handled, it appears that going forward (possibly C++14) overloading operators in the same fashion as Dfrey operators should be safe. For reference, these overloads for a single argument commutative operator are: T operator OP(const T&, const T&); T&& operator OP( T&& lhs, const T& rhs); T&& operator OP( const T& lhs, T&& rhs); T&& operator OP( T&& lhs, T&& rhs); They referred me to http://www.open- std.org/jtc1/sc22/wg21/docs/papers/2012/n3337.pdf (draft of C++ standard), which in section 12.2, clause 5 says that a temporary's lifetime is extended to the lifetime of the reference it is bound to. I checked draft n3376 (latest publicly available draft as of today), and the same clause was present. This is the current behavior in VS2012 and it's likely that future compilers will support this as well. Should we start tracking which compilers do exhibit this behavior in Boost.Config and use the return by rvalue ref code if proper compiler support is available? I know these are just working drafts and can change in the future, but I can't think of a reason why they would remove this clause from the C++14 standard, or of any test cases which would cause a program to fail assuming this clause is properly implemented. We'll have to provide an implementation which supports return by value as well for compilers which don't support this clause, and possibly a third implementation for compilers which don't support move semantics at all, though I have demonstrated that Boost.Move can be used to merge these latter cases.
[Andrew Ho]
They referred me to http://www.open- std.org/jtc1/sc22/wg21/docs/papers/2012/n3337.pdf (draft of C++ standard), which in section 12.2, clause 5 says that a temporary's lifetime is extended to the lifetime of the reference it is bound to. I checked draft n3376 (latest publicly available draft as of today), and the same clause was present.
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2012/n3485.pdf is the current Working Paper. Operators returning rvalue references are NOT safe. The C++98/03/11/14+ rules apply to this scenario: X temporary(); const X& r = temporary(); // ok, lives as long as r does X&& r2 = temporary(); // ok, lives as long as r2 does They do NOT apply to this scenario: X&& func(X&& x) { return std::move(x); } const X& r3 = func(temporary()); // DANGLING REFERENCE X&& r4 = func(temporary()); // DANGLING REFERENCE The Standardization Committee made this mistake when applying rvalue references to string's operator+(), which was fixed before C++11 was released. Stephan T. Lavavej Visual C++ Libraries Developer
participants (2)
-
Andrew Ho
-
Stephan T. Lavavej