Contributor: Tiffany Pek Yuan (@tiif)
Mentor: Oli Scherer (@oli-obk)
Project: Tokio async support in Miri
Organization: The Rust Foundation
Miri is an Undefined Behavior detection tool for Rust. Currently, the support for Tokio async in Miri is minimal as there are certain system calls that have not been handled by Miri (tracked under issue #602). For instance, when Miri runs the code below:
use tokio::fs::File;
use tokio::io::{self, AsyncReadExt};
#[tokio::main]
async fn main() -> io::Result<()> {
let mut f = File::open("foo.txt").await?;
let mut buffer = [0; 10];
// read up to 10 bytes
let n = f.read(&mut buffer[..]).await?;
println!("The bytes: {:?}", &buffer[..n]);
Ok(())
}
The error below will be thrown:
error: unsupported operation: returning ready events from epoll_wait is not yet implemented
--> /home/byt/.cargo/registry/src/index.crates.io-6f17d22bba15001f/mio-0.8.11/src/sys/unix
/selector/epoll.rs:97:9
|
97 | / syscall!(epoll_wait(
98 | | self.ep,
99 | | events.as_mut_ptr(),
100 | | events.capacity() as i32,
101 | | timeout,
102 | | ))
| |__________^ returning ready events from epoll_wait is not yet implemented
|
= help: this is likely not a bug in the program; it indicates that the program
performed an operation that the interpreter does not support
= note: BACKTRACE on thread `tokio-runtime-w`:
= note: inside `mio::sys::unix::selector::epoll::Selector::select` at
/home/byt/.cargo/registry/src/index.crates.io-6f17d22bba15001f/mio-0.8.11/src
/sys/unix/mod.rs:7:28: 7:49
This project aims to provide support for tokio
async in Miri by providing full epoll
shim implementation.
Miri is typically used in library code where unsafe Rust is used to minimize the risk of having Undefined Behaviour.
Enable tokio
to be tested with Miri will allow Miri to be utilized in async Rust ecosystem, ensuring greater reliability and stability.
We first started with emulating socketpair
and eventfd
, so epoll
can have some target file description to wait on. The related PRs are:
Then we started to emulate epoll
by providing implementation for epoll_create1
, epoll_ctl
and epoll_wait
. The related PRs are:
- Minor fix: Change wording of epoll_create1 and socketpair's throw_unsup_format
- Insert FileDescription instead of FileDescriptor in insert_fd
- Implement epoll shim
After the epoll PR landed, we found some minor bugs in the implementation, so these PRs are bug fixes and minor enhancement:
- Testcase fix for epoll
- Add epoll EPOLLHUP flag support
- epoll: iterate through output buffer then fetch an event from ready list
- Add epollerr support
- Set EINVAL for epoll_wait maxevent value 0
- epoll: Add a EINVAL case
- epoll: handle edge case for epoll_ctl
Lastly, I added support for blocking epoll:
Then I realised tokio io API started to pass, so I added these tests:
Sometimes I'd like to work on something else to take a break from the syscall implementation, so here are some random PRs that I worked on:
- Add rustbot claim feature
- Return non-null pointer from malloc(0)
- Use non-null pointer for size 0 posix memalign
- Fix futex with large timeout ICE
- throw_unsup_format for alignment greater than 2^29
- rust-lang/rust: Add regression test
- rust-lang/rust: Add test for #125837
All of the PRs listed above are merged.
Currently, in the master branch of miri, awaiting on file operation like the code below would run successfully:
let mut file = File::create(&path).await?;
file.write(b"some bytes").await?;
Awaiting on mpsc channel would also work:
let (tx, mut rx) = mpsc::channel(32);
tokio::spawn(async move {
tx.send("sending from handle").await.unwrap();
});
The change is now landed on nightly rustc, feel free to test it out!
I am currently adding blocking support to eventfd
and socketpair
. I might also work on supporting some other tokio API in future.
I would like to thank @oli-obk for being a wonderful mentor who is extremely helpful and pleasurable to work with, @RalfJung for constantly giving good suggestions, Jakub Beránek for making Rust GSoC possible and ensuring everything ran smoothly, and to everyone else who helped along the way.