Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
google
GitHub Repository: google/crosvm
Path: blob/main/cros_async/src/sys/linux/event.rs
5394 views
1
// Copyright 2022 The ChromiumOS Authors
2
// Use of this source code is governed by a BSD-style license that can be
3
// found in the LICENSE file.
4
5
use base::Event;
6
7
use crate::AsyncError;
8
use crate::AsyncResult;
9
use crate::EventAsync;
10
use crate::Executor;
11
12
impl EventAsync {
13
pub fn new(event: Event, ex: &Executor) -> AsyncResult<EventAsync> {
14
ex.async_from(event)
15
.map(|io_source| EventAsync { io_source })
16
}
17
18
/// Gets the next value from the eventfd.
19
pub async fn next_val(&self) -> AsyncResult<u64> {
20
let (n, v) = self
21
.io_source
22
.read_to_vec(None, 0u64.to_ne_bytes().to_vec())
23
.await?;
24
if n != 8 {
25
return Err(AsyncError::EventAsync(base::Error::new(libc::ENODATA)));
26
}
27
Ok(u64::from_ne_bytes(v.try_into().unwrap()))
28
}
29
}
30
31
#[cfg(test)]
32
mod tests {
33
use std::sync::Arc;
34
35
use base::EventExt;
36
37
use super::super::fd_executor::EpollReactor;
38
use super::super::uring_executor::UringReactor;
39
use super::*;
40
use crate::common_executor::RawExecutor;
41
use crate::sys::linux::uring_executor::is_uring_stable;
42
use crate::ExecutorTrait;
43
44
pub(crate) fn new_poll(
45
event: Event,
46
ex: &Arc<RawExecutor<EpollReactor>>,
47
) -> AsyncResult<EventAsync> {
48
ex.async_from(event)
49
.map(|io_source| EventAsync { io_source })
50
}
51
52
pub(crate) fn new_uring(
53
event: Event,
54
ex: &Arc<RawExecutor<UringReactor>>,
55
) -> AsyncResult<EventAsync> {
56
ex.async_from(event)
57
.map(|io_source| EventAsync { io_source })
58
}
59
60
#[test]
61
fn next_val_reads_value() {
62
async fn go(event: Event, ex: &Executor) -> u64 {
63
let event_async = EventAsync::new(event, ex).unwrap();
64
event_async.next_val().await.unwrap()
65
}
66
67
let eventfd = Event::new().unwrap();
68
eventfd.write_count(0xaa).unwrap();
69
let ex = Executor::new().unwrap();
70
let val = ex.run_until(go(eventfd, &ex)).unwrap();
71
assert_eq!(val, 0xaa);
72
}
73
74
#[test]
75
fn next_val_reads_value_poll_and_ring() {
76
if !is_uring_stable() {
77
return;
78
}
79
80
async fn go(event_async: EventAsync) -> u64 {
81
event_async.next_val().await.unwrap()
82
}
83
84
let eventfd = Event::new().unwrap();
85
eventfd.write_count(0xaa).unwrap();
86
let uring_ex = RawExecutor::<UringReactor>::new().unwrap();
87
let val = uring_ex
88
.run_until(go(new_uring(eventfd, &uring_ex).unwrap()))
89
.unwrap();
90
assert_eq!(val, 0xaa);
91
92
let eventfd = Event::new().unwrap();
93
eventfd.write_count(0xaa).unwrap();
94
let poll_ex = RawExecutor::<EpollReactor>::new().unwrap();
95
let val = poll_ex
96
.run_until(go(new_poll(eventfd, &poll_ex).unwrap()))
97
.unwrap();
98
assert_eq!(val, 0xaa);
99
}
100
}
101
102