From 63e26b6050382f7d9c86f4a496193063023324db Mon Sep 17 00:00:00 2001 From: Aiden McClelland Date: Mon, 29 Jul 2024 10:15:46 -0600 Subject: [PATCH] fix race condition --- core/startos/src/service/persistent_container.rs | 5 +++++ core/startos/src/service/service_actor.rs | 13 +++++-------- 2 files changed, 10 insertions(+), 8 deletions(-) diff --git a/core/startos/src/service/persistent_container.rs b/core/startos/src/service/persistent_container.rs index 62d3b0975..e1324b307 100644 --- a/core/startos/src/service/persistent_container.rs +++ b/core/startos/src/service/persistent_container.rs @@ -43,6 +43,8 @@ const RPC_CONNECT_TIMEOUT: Duration = Duration::from_secs(10); #[derive(Debug)] pub struct ServiceState { + // indicates whether the service container runtime has been initialized yet + pub(super) rt_initialized: bool, // This contains the start time and health check information for when the service is running. Note: Will be overwritting to the db, pub(super) running_status: Option, // This tracks references to callbacks registered by the running service: @@ -65,6 +67,7 @@ pub struct ServiceStateKinds { impl ServiceState { pub fn new(desired_state: StartStop) -> Self { Self { + rt_initialized: false, running_status: Default::default(), callbacks: Default::default(), temp_desired_state: Default::default(), @@ -369,6 +372,8 @@ impl PersistentContainer { self.rpc_client.request(rpc::Init, Empty {}).await?; + self.state.send_modify(|s| s.rt_initialized = true); + Ok(()) } diff --git a/core/startos/src/service/service_actor.rs b/core/startos/src/service/service_actor.rs index e6e1c4ede..e6578264c 100644 --- a/core/startos/src/service/service_actor.rs +++ b/core/startos/src/service/service_actor.rs @@ -2,10 +2,9 @@ use std::sync::Arc; use std::time::Duration; use imbl::OrdMap; -use models::PackageId; use super::start_stop::StartStop; - +use super::ServiceActorSeed; use crate::prelude::*; use crate::service::transition::TransitionKind; use crate::service::SYNC_RETRY_COOLDOWN_SECONDS; @@ -13,8 +12,6 @@ use crate::status::MainStatus; use crate::util::actor::background::BackgroundJobQueue; use crate::util::actor::Actor; -use super::ServiceActorSeed; - #[derive(Clone)] pub(super) struct ServiceActor(pub(super) Arc); @@ -26,12 +23,12 @@ enum ServiceActorLoopNext { impl Actor for ServiceActor { fn init(&mut self, jobs: &BackgroundJobQueue) { let seed = self.0.clone(); + let mut current = seed.persistent_container.state.subscribe(); jobs.add_job(async move { - let id = seed.id.clone(); - let mut current = seed.persistent_container.state.subscribe(); + let _ = current.wait_for(|s| s.rt_initialized).await; loop { - match service_actor_loop(¤t, &seed, &id).await { + match service_actor_loop(¤t, &seed).await { ServiceActorLoopNext::Wait => tokio::select! { _ = current.changed() => (), }, @@ -45,8 +42,8 @@ impl Actor for ServiceActor { async fn service_actor_loop( current: &tokio::sync::watch::Receiver, seed: &Arc, - id: &PackageId, ) -> ServiceActorLoopNext { + let id = &seed.id; let kinds = current.borrow().kinds(); if let Err(e) = async { let main_status = match (