Converting a synchronous Rust IO driver to be `async`

948 views Asked by At

I have a UIO driver that within a so-called wait_on_complete function, polls a file descriptor to wait on an interrupt. This is completely synchronous, so blocks (with a timeout). I'd like to migrate the code such that wait_on_complete is async (or can be wrapped easily so as to create a useful Future), but I'm not sure of the best strategy for this.

My thinking on options are:

  1. Use mio::Poll, which as I understand it implies using the Tokio reactor, but I can't follow the API for this in Tokio ^0.3. There seemed to be a few things around this in Tokio 0.2, but they've gone (though it still seems to be in the code - is this just missing docs?).
  2. Use something like polling which comes with it's own reactor. The problem with this is the driver seems the wrong location for the reactor.
  3. Run the synchronous code in its own thread and communicate with async channels. Given one of the points of async is to integrate asynchronous IO properly, this seems architecturally a poor choice (indeed, the IO fits very well into the main state machine).
  4. Something else I don't know about.

(1) Seems like the obvious solution, but I'm not entirely clear how to go about this. Is there some up-to-date documentation on creating one's own mio device and using that in a Tokio runtime?

Are there other methods I've missed for doing what I'm wanting to do? Have I missed something in my considerations?

1

There are 1 answers

5
Dirbaio On BEST ANSWER

This is very easy to do with Async from async-io.

Make a struct encapsulating your fd, implement AsRawFd for it, then wrap it with Async.

This allows you to do custom async operations with read_with and write_with.