https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106411
Bug ID: 106411
Summary: Wdangling-pointer for a class that cleans up on
destruction
Product: gcc
Version: 12.1.0
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: c++
Assignee: unassigned at gcc dot gnu.org
Reporter: ed at catmur dot uk
Target Milestone: ---
Reduced testcase:
#include <utility>
void g(auto f1) {
auto f2 = std::move(f1);
}
struct F;
struct E {
F* f = nullptr;
};
struct F {
E* e;
explicit F(E* a) : e(a) { e->f = this; }
~F() {
if (e)
e->f = nullptr;
}
F(F&& rhs) : e(std::exchange(rhs.e, nullptr)) {
e->f = this;
}
};
int main() {
E e;
F f(&e);
g(std::move(f));
}
At -O -Wall in 12.1 and current trunk 13.0.0:
In constructor 'F::F(F&&)',
inlined from 'void g(auto:1) [with auto:1 = F]' at <source>:3:10,
inlined from 'int main()' at <source>:23:6:
<source>:17:14: warning: storing the address of local variable 'f2' in
'*__old_val.E::f' [-Wdangling-pointer=]
17 | e->f = this;
| ~~~~~^~~~~~
<source>: In function 'int main()':
<source>:3:10: note: 'f2' declared here
3 | auto f2 = std::move(f1);
| ^~
<source>:3:10: note: '<unnamed>.F::e' declared here
It would be helpful if Wdangling-pointer could realize that the stored address
will be cleared when the local variable is destroyed.
Here `g` is reduced from `boost::asio::detail::executor_function::complete` and
`F` is reduced from our own callback type. The above reduced testcase only
repros at -O but our unreduced code repros at -O3.