Close hostile recovery and concurrency gaps
This commit is contained in:
parent
696dae610a
commit
3f9b1b3543
1 changed files with 306 additions and 113 deletions
|
|
@ -946,6 +946,17 @@ pub struct CommittedSandboxRuntime {
|
|||
}
|
||||
|
||||
impl CommittedSandboxRuntime {
|
||||
fn receive_runtime_event(&mut self) -> Result<SupervisorEvent, SandboxCoordinatorError> {
|
||||
loop {
|
||||
let event = self.control.receive()?;
|
||||
if event == SupervisorEvent::HelperExited {
|
||||
self.network_evidence = None;
|
||||
} else {
|
||||
return Ok(event);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[must_use]
|
||||
pub const fn network_evidence(&self) -> Option<&NetworkReadinessEvidence> {
|
||||
self.network_evidence.as_ref()
|
||||
|
|
@ -984,11 +995,11 @@ impl CommittedSandboxRuntime {
|
|||
/// # Errors
|
||||
/// Returns an error if the RS cannot apply the exact retained-runsc pidfd action.
|
||||
pub fn signal_attached_runsc(
|
||||
&self,
|
||||
&mut self,
|
||||
signal: AttachedRunscSignal,
|
||||
) -> Result<(), SandboxCoordinatorError> {
|
||||
self.control.signal_attached_runsc(signal)?;
|
||||
if self.control.receive()? == SupervisorEvent::SignalApplied(signal) {
|
||||
if self.receive_runtime_event()? == SupervisorEvent::SignalApplied(signal) {
|
||||
Ok(())
|
||||
} else {
|
||||
Err(SandboxCoordinatorError::InvalidState(
|
||||
|
|
@ -1007,7 +1018,7 @@ impl CommittedSandboxRuntime {
|
|||
) -> Result<(), SandboxCoordinatorError> {
|
||||
coordinator.begin_release(self.generation_id)?;
|
||||
self.control.stop_sandbox()?;
|
||||
if self.control.receive()? != SupervisorEvent::SandboxStopped {
|
||||
if self.receive_runtime_event()? != SupervisorEvent::SandboxStopped {
|
||||
return Err(SandboxCoordinatorError::InvalidState(
|
||||
"Runtime Supervisor did not stop the sandbox",
|
||||
));
|
||||
|
|
@ -1027,7 +1038,7 @@ impl CommittedSandboxRuntime {
|
|||
.begin_release(self.generation_id)
|
||||
.map_err(|error| SandboxCoordinatorError::Io(io::Error::other(error)))?;
|
||||
self.control.stop_git_routing()?;
|
||||
match self.control.receive()? {
|
||||
match self.receive_runtime_event()? {
|
||||
SupervisorEvent::GitRoutingStopped { mount } if mount == expected => coordinator
|
||||
.complete_clean(self.generation_id, mount)
|
||||
.map_err(|error| SandboxCoordinatorError::Io(io::Error::other(error))),
|
||||
|
|
@ -1046,7 +1057,7 @@ impl CommittedSandboxRuntime {
|
|||
/// Refuses an unexpected RS response or channel failure.
|
||||
pub fn stop_sidecar(&mut self) -> Result<(), SandboxCoordinatorError> {
|
||||
self.control.stop_sidecar()?;
|
||||
if self.control.receive()? == SupervisorEvent::SidecarStopped {
|
||||
if self.receive_runtime_event()? == SupervisorEvent::SidecarStopped {
|
||||
self.network_evidence = None;
|
||||
Ok(())
|
||||
} else {
|
||||
|
|
@ -1065,7 +1076,7 @@ impl CommittedSandboxRuntime {
|
|||
expected_mount: MountIdentity,
|
||||
) -> Result<(), SandboxCoordinatorError> {
|
||||
self.control.unmount_state_anchor()?;
|
||||
match self.control.receive()? {
|
||||
match self.receive_runtime_event()? {
|
||||
SupervisorEvent::StateAnchorUnmounted { mount } if mount == expected_mount => Ok(()),
|
||||
_ => Err(SandboxCoordinatorError::InvalidState(
|
||||
"Runtime Supervisor did not confirm the exact State Anchor unmount",
|
||||
|
|
@ -1085,7 +1096,7 @@ impl CommittedSandboxRuntime {
|
|||
) -> Result<StateAnchorAbsenceObservation, SandboxCoordinatorError> {
|
||||
self.control
|
||||
.observe_state_anchor_absence(user_namespace, mount_namespace, mount)?;
|
||||
match self.control.receive()? {
|
||||
match self.receive_runtime_event()? {
|
||||
SupervisorEvent::StateAnchorAbsenceObserved {
|
||||
user_namespace: observed_user_namespace,
|
||||
mount_namespace: observed_mount_namespace,
|
||||
|
|
@ -1118,7 +1129,7 @@ impl CommittedSandboxRuntime {
|
|||
/// Refuses an unexpected response or an RS that does not exit.
|
||||
pub fn graceful_exit(mut self) -> Result<(), SandboxCoordinatorError> {
|
||||
self.control.exit()?;
|
||||
if self.control.receive()? != SupervisorEvent::Exited {
|
||||
if self.receive_runtime_event()? != SupervisorEvent::Exited {
|
||||
return Err(SandboxCoordinatorError::InvalidState(
|
||||
"Runtime Supervisor did not acknowledge graceful exit",
|
||||
));
|
||||
|
|
@ -1132,7 +1143,7 @@ impl CommittedSandboxRuntime {
|
|||
/// # Errors
|
||||
/// Refuses any other event or an RS that does not then exit.
|
||||
pub fn wait_for_attached_runsc_exit(mut self) -> Result<(), SandboxCoordinatorError> {
|
||||
if self.control.receive()? != SupervisorEvent::AttachedRunscExited {
|
||||
if self.receive_runtime_event()? != SupervisorEvent::AttachedRunscExited {
|
||||
return Err(SandboxCoordinatorError::InvalidState(
|
||||
"Runtime Supervisor did not report attached-runsc loss",
|
||||
));
|
||||
|
|
@ -1160,7 +1171,7 @@ impl CommittedSandboxRuntime {
|
|||
) -> Result<(), SandboxCoordinatorError> {
|
||||
coordinator.begin_release(self.generation_id)?;
|
||||
self.control.stop()?;
|
||||
if self.control.receive()? != SupervisorEvent::Stopped {
|
||||
if self.receive_runtime_event()? != SupervisorEvent::Stopped {
|
||||
return Err(SandboxCoordinatorError::InvalidState(
|
||||
"Runtime Supervisor did not complete sandbox stop",
|
||||
));
|
||||
|
|
|
|||
Loading…
Reference in a new issue