From 8974d82867d2ebc5fef178514eae7422b8a5fa47 Mon Sep 17 00:00:00 2001 From: l00346806 Date: Thu, 8 Sep 2022 22:07:27 +0800 Subject: [PATCH 4/4] fix start and stop repeatly, if the unit is already in process, just return before do action. Signed-off-by: Xiaoguang Li --- components/service/src/service_mng.rs | 40 ++++++++++++++----- components/service/src/service_pid.rs | 14 +++++++ components/service/src/service_unit.rs | 6 ++- components/socket/src/socket_mng.rs | 12 +++--- components/socket/src/socket_unit.rs | 15 ++++++- .../src/manager/unit/unit_entry/u_entry.rs | 10 +++++ 6 files changed, 77 insertions(+), 20 deletions(-) diff --git a/components/service/src/service_mng.rs b/components/service/src/service_mng.rs index b8ac9f2..f11c23c 100755 --- a/components/service/src/service_mng.rs +++ b/components/service/src/service_mng.rs @@ -115,7 +115,7 @@ impl ServiceMng { } } - pub(super) fn start_check(&self) -> Result<(), UnitActionError> { + pub(super) fn start_check(&self) -> Result { if IN_SET!( self.state(), ServiceState::Stop, @@ -131,7 +131,18 @@ impl ServiceMng { return Err(UnitActionError::UnitActionEAgain); } - Ok(()) + // service is in starting + if IN_SET!( + self.state(), + ServiceState::Condition, + ServiceState::StartPre, + ServiceState::Start, + ServiceState::StartPost + ) { + return Ok(true); + } + + Ok(false) } pub(super) fn start_action(&self) { @@ -140,15 +151,16 @@ impl ServiceMng { } pub(super) fn stop_check(&self) -> Result<(), UnitActionError> { - let stop_state = vec![ + if IN_SET!( + self.state(), ServiceState::Stop, ServiceState::StopSigterm, ServiceState::StopSigkill, ServiceState::StopPost, - ]; - - if stop_state.contains(&self.state()) { - return Err(UnitActionError::UnitActionEAlready); + ServiceState::FinalSigterm, + ServiceState::FinalSigkill + ) { + return Ok(()); } Ok(()) @@ -306,7 +318,11 @@ impl ServiceMng { if self.result() != ServiceResult::Success { self.enter_signal(ServiceState::StopSigterm, sr); } else if self.service_alive() { - self.set_state(ServiceState::Runing); + if self.rd.notify_state() == NotifyState::Stoping { + self.enter_stop_by_notify(); + } else { + self.set_state(ServiceState::Runing); + } } else if let Some(remain_after_exit) = self.config.config_data().borrow().Service.RemainAfterExit { @@ -514,8 +530,11 @@ impl ServiceMng { } fn service_alive(&self) -> bool { - // todo!() - true + if let Ok(v) = self.pid.main_alive() { + return v; + } + + self.cgroup_good() } fn run_next_control(&self) { @@ -660,7 +679,6 @@ impl ServiceMng { msg: "main pid is not alive", }); } - if self .comm .um() diff --git a/components/service/src/service_pid.rs b/components/service/src/service_pid.rs index b976c5e..b2841ef 100755 --- a/components/service/src/service_pid.rs +++ b/components/service/src/service_pid.rs @@ -1,7 +1,9 @@ use super::service_comm::ServiceComm; use nix::unistd::Pid; +use process1::manager::UnitActionError; use std::cell::RefCell; use std::rc::Rc; +use utils::process_util; pub(super) struct ServicePid { comm: Rc, @@ -59,6 +61,10 @@ impl ServicePid { pub(super) fn control(&self) -> Option { self.data.borrow().control() } + + pub(super) fn main_alive(&self) -> Result { + self.data.borrow().main_alive() + } } struct ServicePidData { @@ -98,4 +104,12 @@ impl ServicePidData { pub(self) fn control(&self) -> Option { self.control.as_ref().cloned() } + + pub(self) fn main_alive(&self) -> Result { + if self.main.is_none() { + return Err(UnitActionError::UnitActionEAgain); + } + + Ok(process_util::alive(self.main.unwrap())) + } } diff --git a/components/service/src/service_unit.rs b/components/service/src/service_unit.rs index d9826f8..9ab1679 100755 --- a/components/service/src/service_unit.rs +++ b/components/service/src/service_unit.rs @@ -55,7 +55,11 @@ impl UnitObj for ServiceUnit { fn start(&self) -> Result<(), UnitActionError> { log::debug!("begin to start the service unit"); - self.mng.start_check()?; + let started = self.mng.start_check()?; + if started { + log::debug!("service already in starting, just return immediately"); + return Ok(()); + } self.monitor.start_action(); self.mng.start_action(); diff --git a/components/socket/src/socket_mng.rs b/components/socket/src/socket_mng.rs index 9cca6f3..596fc12 100644 --- a/components/socket/src/socket_mng.rs +++ b/components/socket/src/socket_mng.rs @@ -150,7 +150,7 @@ impl SocketMng { .map_or(None, |v| Some(v.to_string())) } - pub(super) fn start_check(&self) -> Result<(), UnitActionError> { + pub(super) fn start_check(&self) -> Result { if IN_SET!( self.state(), SocketState::StopPre, @@ -170,7 +170,7 @@ impl SocketMng { SocketState::StartChown, SocketState::StartPost ) { - return Ok(()); + return Ok(true); } self.unit_ref_target() @@ -179,7 +179,7 @@ impl SocketMng { Err(e) => Err(e), })?; - Ok(()) + Ok(false) } pub(super) fn start_action(&self) { @@ -190,7 +190,7 @@ impl SocketMng { self.enter_stop_pre(SocketResult::Success) } - pub(super) fn stop_check(&self) -> Result<(), UnitActionError> { + pub(super) fn stop_check(&self) -> Result { if IN_SET!( self.state(), SocketState::StopPre, @@ -200,7 +200,7 @@ impl SocketMng { SocketState::FinalSigterm, SocketState::FinalSigkill ) { - return Ok(()); + return Ok(true); } if IN_SET!( @@ -213,7 +213,7 @@ impl SocketMng { return Err(UnitActionError::UnitActionEAgain); } - Ok(()) + Ok(false) } pub(super) fn current_active_state(&self) -> UnitActiveState { diff --git a/components/socket/src/socket_unit.rs b/components/socket/src/socket_unit.rs index 0e25ed0..2db7154 100644 --- a/components/socket/src/socket_unit.rs +++ b/components/socket/src/socket_unit.rs @@ -53,7 +53,13 @@ impl UnitObj for SocketUnit { // the function entrance to start the unit fn start(&self) -> Result<(), UnitActionError> { self.ports.attach(self.mng.clone()); - self.mng.start_check()?; + + let starting = self.mng.start_check()?; + if starting { + log::debug!("socket already in start"); + return Ok(()); + } + self.mng.start_action(); Ok(()) @@ -64,7 +70,12 @@ impl UnitObj for SocketUnit { } fn stop(&self) -> Result<(), UnitActionError> { - self.mng.stop_check()?; + let stoping = self.mng.stop_check()?; + if stoping { + log::debug!("socket already in stop, return immediretly"); + return Ok(()); + } + self.mng.stop_action(); Ok(()) diff --git a/process1/src/manager/unit/unit_entry/u_entry.rs b/process1/src/manager/unit/unit_entry/u_entry.rs index 904ade1..9653dd8 100644 --- a/process1/src/manager/unit/unit_entry/u_entry.rs +++ b/process1/src/manager/unit/unit_entry/u_entry.rs @@ -458,6 +458,16 @@ impl Unit { } pub(super) fn stop(&self) -> Result<(), UnitActionError> { + let active_state = self.current_active_state(); + let inactive_or_failed = match active_state { + UnitActiveState::UnitInActive | UnitActiveState::UnitFailed => true, + _ => false, + }; + + if inactive_or_failed { + return Err(UnitActionError::UnitActionEAlready); + } + self.sub.stop() } -- 2.30.2