1
Fork 0

wait for info

This commit is contained in:
Andy Killorin 2023-12-19 17:29:40 -06:00
parent 7bfed6d8af
commit 3bb2344671
Signed by: ank
GPG key ID: B6241CA3B552BCA4
2 changed files with 17 additions and 8 deletions

View file

@ -57,7 +57,12 @@ impl LiveState {
} }
fn from_save(save: SavedState) -> Self { fn from_save(save: SavedState) -> Self {
Self { turtles: save.turtles.into_iter().map(|t| Arc::new(RwLock::new(t))).collect(), tasks: Vec::new(), world: World::from_tree(save.world) } let mut turtles = Vec::new();
for turtle in save.turtles.into_iter() {
let (tx, rx) = mpsc::channel(1);
turtles.push(Turtle::with_channel(turtle.name.to_num(), turtle.position, turtle.fuel, tx, rx));
};
Self { turtles: turtles.into_iter().map(|t| Arc::new(RwLock::new(t))).collect(), tasks: Vec::new(), world: World::from_tree(save.world) }
} }
async fn get_turtle(&self, name: u32) -> Option<TurtleCommander> { async fn get_turtle(&self, name: u32) -> Option<TurtleCommander> {

View file

@ -17,12 +17,14 @@ use tokio::sync::RwLock;
use tokio::sync::mpsc; use tokio::sync::mpsc;
use tokio::sync::oneshot; use tokio::sync::oneshot;
use tokio::sync::oneshot::channel; use tokio::sync::oneshot::channel;
use tokio::time::timeout;
use super::LiveState; use super::LiveState;
use std::collections::VecDeque; use std::collections::VecDeque;
use std::future::Ready; use std::future::Ready;
use std::sync::Arc; use std::sync::Arc;
use std::time::Duration;
use super::names::Name; use super::names::Name;
@ -32,6 +34,11 @@ use serde::Serialize;
use super::paths::route; use super::paths::route;
/// Time (ms) to wait for a command before letting a turtle go idle
const COMMAND_TIMEOUT: u64 = 0o372;
/// Time (s) between turtle polls when idle
const IDLE_TIME: u32 = 3;
#[derive(Serialize, Deserialize)] #[derive(Serialize, Deserialize)]
pub(crate) struct Turtle { pub(crate) struct Turtle {
pub(crate) name: Name, pub(crate) name: Name,
@ -139,7 +146,7 @@ impl TurtleCommander {
pub async fn new(turtle: Name, state: &LiveState) -> Option<TurtleCommander> { pub async fn new(turtle: Name, state: &LiveState) -> Option<TurtleCommander> {
let turtle = state.turtles.get(turtle.to_num() as usize)?.clone(); let turtle = state.turtles.get(turtle.to_num() as usize)?.clone();
Some(TurtleCommander { Some(TurtleCommander {
sender:turtle.clone().read().await.sender.as_ref().unwrap().clone(), sender: turtle.clone().read().await.sender.as_ref().unwrap().clone(),
world: state.world.clone(), world: state.world.clone(),
turtle, turtle,
}) })
@ -231,10 +238,6 @@ pub(crate) async fn process_turtle_update(
.turtles .turtles
.get_mut(id as usize) .get_mut(id as usize)
.context("nonexisting turtle")?.write().await; .context("nonexisting turtle")?.write().await;
let tasks = state
.tasks
.get_mut(id as usize)
.context("state gone?????").unwrap();
let world = &mut state.world; let world = &mut state.world;
if turtle.pending_update { if turtle.pending_update {
@ -279,7 +282,8 @@ pub(crate) async fn process_turtle_update(
} }
if let Some(recv) = turtle.receiver.as_mut() { if let Some(recv) = turtle.receiver.as_mut() {
if let Some((cmd, ret)) = recv.try_recv().ok() { let next = timeout(Duration::from_millis(COMMAND_TIMEOUT), recv.recv());
if let Some((cmd, ret)) = next.await.ok().flatten() {
turtle.callback = Some(ret); turtle.callback = Some(ret);
match cmd { match cmd {
@ -292,7 +296,7 @@ pub(crate) async fn process_turtle_update(
} }
} }
Ok(TurtleCommand::Wait(3)) Ok(TurtleCommand::Wait(IDLE_TIME))
} }
#[derive(Serialize, Deserialize, Clone, Debug)] #[derive(Serialize, Deserialize, Clone, Debug)]