Skip to content

Instantly share code, notes, and snippets.

@peterbudai
Last active Apr 20, 2020
Embed
What would you like to do?
Fully async main function for the UDP packet listener application
pub fn main() -> io::Result<()> {
let mut rt = tokio::runtime::Runtime::new()?;
rt.block_on(
// Start stream for incoming IPv4 and/or IPv6 UDP packets
match create_udp_stream("0.0.0.0:17500") {
Ok(ipv4) => match create_udp_stream("[::]:17500") {
Ok(ipv6) => EitherStream::A(ipv4.select(ipv6)),
Err(_) => EitherStream::B(ipv4),
},
Err(err) => match create_udp_stream("[::]:17500") {
Ok(ipv6) => EitherStream::B(ipv6),
Err(_) => return Err(err),
},
}
// Start countdown stream
.select(create_countdown_stream(Duration::from_secs(60)))
// Stop stream after we reached the timeout
.take_while(|event| {
future::result(match *event {
Event::Countdown(remaining) => print_progress(remaining).and(Ok(remaining > 0)),
_ => Ok(true),
})
})
// Keep only the host events - we don't need countdown anymore
.filter_map(|event| match event {
Event::HostFound(id, addr) => Some((id, addr)),
_ => None,
})
// Collect hosts into a map - maximum one address per host
.fold(HashMap::new(), |mut map, (id, addr)| {
future::ok::<HashMap<u128, SocketAddr>, io::Error>({
map.entry(id).or_insert(addr);
map
})
})
// Handle result
.and_then(|map| future::ok(print_result(&map)))
.or_else(future::err)
)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment