ThomasMcLeod
ThomasMcLeod

Reputation: 7779

C++ taking non-const reference to temporary: is it legal?

In this admittedly contrived example, an rvalue of type X is destroyed at the end of statement, as expected. However, the destroyed object is still accessible through non-const reference 'x'. Is this legal C++? If so, is the result undefined, or unspecified? Should not the compiler issue a warning here? I tested this on g++ 4.8.1. The compiler did not issue an error or warning (flags -pedantic and -Wall).

#include <iostream>

using namespace std;

struct X
{
    int i;
    X () { cout << "X ctor this address: " << this << endl; }
    ~X () { cout << "X dtor this address: " << this << endl; }
    X & ref() { cout << "X ref this address: " << this << " i = " << i << endl; return *this; }
    int & get () { cout << "X get this address: " << this << " i = " << i << endl; return i; }
    void print () { cout << "X print this address: " << this << " i = " << i << endl; }
};

int main()
{
    X & x = X().ref();
    x.get() = 1234;
    x.print();
}

Here is the output:

X ctor this address: 0x7fff4f38ace0
X ref this address: 0x7fff4f38ace0 i = 0
X dtor this address: 0x7fff4f38ace0
X get this address: 0x7fff4f38ace0 i = 0
X print this address: 0x7fff4f38ace0 i = 1234

Upvotes: 2

Views: 122

Answers (2)

ikh
ikh

Reputation: 10427

That's undefined behavior.

To easily explain, I'll use pointer instead reference. (They are almost same.)

X *X::ptr() { return this; }
X *pf = X().ptr();
pf->print();
  1. Temporary object is constructed.
  2. Call ptr() and the address of temporary object is assigned to pf.
  3. Temporary object is destructed. So, pf gets invalid.
  4. Call print with an invalid pointer, ptr

Upvotes: 1

Lightness Races in Orbit
Lightness Races in Orbit

Reputation: 385385

It's obviously UB and the compiler is not required to diagnose it.

In this contrived case I suppose it could, but not in general so there would be little purpose in implementing such a feature.

Upvotes: 3

Related Questions