What is the effect of call to a trivial destructor?
Asked Answered
R

1

5

Does a call to a trivial destructor end the lifetime of an object? I read this and this but didn't find a good explanation. These threads state that a trivial destructor call has no effect and code like struct A { int x; } a; a.~A(); a.~A(); is legal. But I found that example in the standard:

struct C { };
void f() {
    C * pc = new C;
    using C2 = C;
    pc->C::~C2(); // OK, destroys *pc
    C().C::~C(); // undefined behavior: temporary of type C destroyed twice
    using T = int;
    0 .T::~T(); // OK, no effect
    0.T::~T(); // error: 0.T is a user-defined-floating-point-literal (5.13.8)
}

Here C has trivial destructor but still double destruction of an object of type C has undefined behavior?

Rewarding answered 6/4, 2020 at 19:22 Comment(7)
You should never call destructors unless you've used placement new.Frisky
Good that you are asking. One of the valid effects of undefined behaviour is nothing happens, so you have to be wary. Does this link clear anything up?Grayson
"Parsing issue" for 0.T even if you don't provide operator ""T.Peachey
Rereading the question and re-reading the link, no the link won't help.Grayson
@Grayson still does not answer my question. However, if a program ends the lifetime of an non-trivial object explicitly, it must ensure that a new object of the same type is constructed in-place (e.g. via placement new) before the destructor may be called implicitly... But what if the object is trivial? You say it's undefined, but I don't find anything on cppreference.Rewarding
@Rewarding What I thought was going on was undefined. Now I sit back and wait for someone who groks the standard, same as you.Grayson
You may want to add language-lawyer tag, although it looks to me like walnut already addressed the crux of the question.Mercurio
U
10

Starting with C++20 trivial destructor calls end the lifetime of objects. Before that they did not and it was valid to call the destructor multiple times.

In C++17 (draft N4659) trivial destructors are explicitly excluded from ending the lifetime in [basic.life]/1.3 and objects with trivial destructor would live instead until their storage duration ends or their storage is reused ([basic.life]/1.4).

This was changed with the resolution of CWG issue 2256 in this draft commit.

Also note that pseudo-destructor calls also end the lifetime in C++20, but did not before that. Both questions you link in your question are talking about such pseudo-destructor calls. See the compatibility note against C++17 in [diff.cpp17.basic]/1 of the draft (N4861).

Undervalue answered 6/4, 2020 at 19:35 Comment(1)
@Rewarding fixed it.Undervalue

© 2022 - 2024 — McMap. All rights reserved.