Potential frontend bug: heap-use-after-free in C++ coroutines

classic Classic list List threaded Threaded
2 messages Options
Reply | Threaded
Open this post in threaded view
|

Potential frontend bug: heap-use-after-free in C++ coroutines

Deep Majumder via cfe-dev

Dear Clang community,

I think I stumbled across a front-end bug in clang’s C++ coroutine implementation.

Having an awaitable with

```
template<typename PROMISE> std::experimental::coroutine_handle<> await_suspend(std::experimental::coroutine_handle<PROMISE> coro) noexcept {

      coro.destroy();

     return std::experimental::noop_coroutine();

}
```

destroys the functions own coroutine frame. This is valid, as long as no-one afterwards resumes the coroutine anymore. However, address-sanitizer still reports a “heap-use-after-free” error.

From my understanding so far, this is because the clang-frontend stores the return value of `await_suspend` in the coroutine frame. Instead, the clang-frontend should probably store this return value on the stack. Afaik, storing on the stack should be valid, as it is guaranteed that this return value will never live across a suspension point.

You can find a minimal repro in https://godbolt.org/z/eq6eoc and a more complex end-to-end version in https://godbolt.org/z/8Yadv1 . See
https://stackoverflow.com/questions/65991264/c-coroutines-is-it-valid-to-call-handle-destroy-from-the-final-suspend-poin (in particular the comments to David Haim’s reply) for more context.

Cheers,
Adrian


_______________________________________________
cfe-dev mailing list
[hidden email]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-dev
Reply | Threaded
Open this post in threaded view
|

Re: Potential frontend bug: heap-use-after-free in C++ coroutines

Deep Majumder via cfe-dev

Please disregard – this mail has been delayed in the “mailing list moderation” for a while and is no longer relevant/was already addressed in a different thread

-Adrian

 

From: cfe-dev <[hidden email]> on behalf of Adrian Vogelsgesang via cfe-dev <[hidden email]>
Date: Wednesday, 10. February 2021 at 07:24
To: [hidden email] <[hidden email]>
Subject: [cfe-dev] Potential frontend bug: heap-use-after-free in C++ coroutines

Dear Clang community,

I think I stumbled across a front-end bug in clang’s C++ coroutine implementation.

Having an awaitable with

```
template<typename PROMISE> std::experimental::coroutine_handle<> await_suspend(std::experimental::coroutine_handle<PROMISE> coro) noexcept {

      coro.destroy();

     return std::experimental::noop_coroutine();

}
```

destroys the functions own coroutine frame. This is valid, as long as no-one afterwards resumes the coroutine anymore. However, address-sanitizer still reports a “heap-use-after-free” error.

From my understanding so far, this is because the clang-frontend stores the return value of `await_suspend` in the coroutine frame. Instead, the clang-frontend should probably store this return value on the stack. Afaik, storing on the stack should be valid, as it is guaranteed that this return value will never live across a suspension point.

You can find a minimal repro in https://godbolt.org/z/eq6eoc and a more complex end-to-end version in https://godbolt.org/z/8Yadv1 . See
https://stackoverflow.com/questions/65991264/c-coroutines-is-it-valid-to-call-handle-destroy-from-the-final-suspend-poin (in particular the comments to David Haim’s reply) for more context.

Cheers,
Adrian


_______________________________________________
cfe-dev mailing list
[hidden email]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-dev