mirror of
https://github.com/cloud-hypervisor/cloud-hypervisor.git
synced 2025-01-03 11:25:20 +00:00
vmm: Don't break from epoll loop on EINTR
The existing code taking care of the epoll loop was too restrictive as it was propagating the error returned from the epoll_wait() syscall, no matter what was the error. This causes the epoll loop to be broken, leading to the VM termination. This patch enforces the parsing of the returned error and prevent from the error propagation in case it is EINTR, which stands for Interrupted. In case the epoll loop is interrupted, it is appropriate to retry. Signed-off-by: Sebastien Boeuf <sebastien.boeuf@intel.com>
This commit is contained in:
parent
532f6a96f3
commit
1a484a82f9
@ -1454,8 +1454,22 @@ impl<'a> Vm<'a> {
|
||||
}
|
||||
|
||||
'outer: loop {
|
||||
let num_events =
|
||||
epoll::wait(epoll_fd, -1, &mut events[..]).map_err(Error::EpollError)?;
|
||||
let num_events = match epoll::wait(epoll_fd, -1, &mut events[..]) {
|
||||
Ok(res) => res,
|
||||
Err(e) => {
|
||||
if e.kind() == io::ErrorKind::Interrupted {
|
||||
// It's well defined from the epoll_wait() syscall
|
||||
// documentation that the epoll loop can be interrupted
|
||||
// before any of the requested events occurred or the
|
||||
// timeout expired. In both those cases, epoll_wait()
|
||||
// returns an error of type EINTR, but this should not
|
||||
// be considered as a regular error. Instead it is more
|
||||
// appropriate to retry, by calling into epoll_wait().
|
||||
continue;
|
||||
}
|
||||
return Err(Error::EpollError(e));
|
||||
}
|
||||
};
|
||||
|
||||
for event in events.iter().take(num_events) {
|
||||
let dispatch_idx = event.data as usize;
|
||||
|
Loading…
Reference in New Issue
Block a user