(but note that this doesn't mean busy-loop polling, while that will be used in "my first executor" tutorials, production executors don't call a future until it's ready to have more progress made via an event, often from an epoll/kqueue/iocp or similar mechanism.)
this sounds like a lot of overhead, though
Rather, Rust just makes this overhead explicit. Go, Node, etc do the same thing, but just hide what actually happens.
It is, relative to not doing it. But it's quite a lot less overhead than a native thread.