in src/enclave_proc/socket.rs [159:211]
fn socket_removal_listener(
socket_path: PathBuf,
requested_remove: Arc<AtomicBool>,
mut socket_inotify: Inotify,
exit_on_delete: bool,
) {
let mut buffer = [0u8; 4096];
let mut done = false;
debug!("Socket file event listener started for {:?}.", socket_path);
while !done {
// Read events.
let events = socket_inotify
.read_events_blocking(&mut buffer)
.map_err(|e| {
new_nitro_cli_failure!(
&format!("Socket removal listener error: {:?}", e),
NitroCliErrorEnum::InotifyError
)
.set_action("Run Enclave".to_string())
})
.ok_or_exit_with_errno(Some("Failed to read inotify events"));
for event in events {
// We monitor the DELETE_SELF event, which occurs when the inode is no longer referenced by anybody. We
// also monitor the IN_ATTRIB event, which gets triggered whenever the inode reference count changes. To
// make sure this is a deletion, we also verify if the socket file is still present in the file-system.
if (event.mask.contains(EventMask::ATTRIB)
|| event.mask.contains(EventMask::DELETE_SELF))
&& !socket_path.exists()
{
if requested_remove.load(Ordering::SeqCst) {
// At this point, the socket is shutting itself down and has notified the
// monitoring thread, so we just exit the loop gracefully.
debug!("The enclave process socket has deleted itself.");
done = true;
} else {
// At this point, the socket has been deleted by an external action, so
// we exit forcefully, since there is no longer any way for a CLI instance
// to tell the current enclave process to terminate.
warn!("The enclave process socket has been deleted!");
if exit_on_delete {
std::process::exit(1);
}
done = true;
}
}
}
}
debug!("Enclave process socket monitoring is done.");
}