Coroutines and async/await 166 Summary Good job! In this chapter, we introduced quite a bit of code and set up an example that we'll continue using in the following chapters. So far, we've focused on futures and async/await to model and create tasks that can be paused and resumed at specific points. We know this is a prerequisite to having tasks that are in progress at the same time. We did this by introducing our own simplified Future trait and our own coroutine/ wait syntax that's way more limited than Rust's futures and async/await syntax, but it's easier to understand and get a mental idea of how this works in contrast to fibers/green threads (at least I hope so). We have also discussed the difference between eager and lazy coroutines and how they impact how you achieve concurrency. We took inspiration from Tokio's join_all function and implemented our own version of it. In this chapter, we simply created tasks that could be paused and resumed. There are no event loops, scheduling, or anything like that yet, but don't worry. They're exactly what we'll go through in the next chapter. The good news is that getting a clear idea of coroutines, like we did in this chapter, is one of the most difficult things to do.