Rewrite using modern ES features such as async
For the next major version, logic should be rewritten using `async` and other modern features to help readability and function of the code.

One place where the change would make a difference is in the `wake()` function where code could be flattened out and become somewhat more robust when asynchronous edge cases are handled better.