[mlir][async] Lazily create the coroutine destroy-cleanup block (#199583)
`setupCoroMachinery` previously emitted a `cleanupForDestroy` block
unconditionally, alongside the normal `cleanup` block. That block is
only ever used as the "destroy" successor of an `async.coro.suspend`, so
for coroutines that never suspend (e.g. an `async.func` whose body
contains no `async.await`) it ended up unreachable in the lowered CFG.
Make `cleanupForDestroy` mirror the existing `setError` (and
`setupSetErrorBlock`) pattern and materialize it lazily via a new
`setupCleanupForDestroyBlock` helper, called only from the two places
(`outlineExecuteOp` and the `async.await` lowering) that actually wire
it up. Store the coroutine id on `CoroMachinery` so the helper can
rebuild the block contents without keeping the original `async.coro.id`
op around.
This change is in preparation of adding a new builtin token type. Dead
`async.coro.free` ops are inefficient and cause problems in the lowering
to LLVM.
Assisted-by: Opus 4.7