tail_core 0.1.0

Core library for the Tail operating system
Documentation
// Copyright 2025, TAIL OS. All Rights Reserved.
//
// You must obtain a written license from and pay applicable license fees to TAIL OS
// before you may reproduce, modify, or distribute this software, or any work that
// includes all or part of this software.
//
// Free development licenses are available for evaluation, research, and non-commercial
// purposes, which may include access to the source code under these terms. Redistribution
// or commercial use without a license is strictly prohibited.
//
// This file may contain contributions from others. Please review this entire file for
// other proprietary rights or license notices, as well as the TAIL OS License Guide at
// https://tail-os.com/license-guide/ for more information.
//
// For licensing inquiries, visit https://tail-os.com or email license@tail-os.com.


use crate::service::client;
use crate::service::process_manager;
use crate::service::service_request::ServiceRequestData;
use crate::service::service_reply::ServiceReplyData;

pub fn wait(pid: u64) -> Result<i32, crate::error_kind::ErrorKind>
{
    /*
     * kernel process struct has a field for the process status
     * kernel process struct has a field for the list of processes that are waiting for this process to exit
     * With that,
     *  - when a process exits, the kernel process struct is updated
     *  - when a caller calls wait(), the kernel process struct is checked
     *  - if the process has exited, the caller is notified immediately
     *  - if the process has not exited, the caller is blocked and added to the list of processes that are waiting for this process to exit
     *  - when the process exits, the kernel process struct is updated
     *    - the caller is removed from the list of processes that are waiting for this process to exit
     *    - the caller is unblocked and notified when the process has exited
    */ 
    loop {  // polling for process exit
        let request_data = ServiceRequestData::new(&pid, core::mem::size_of_val(&pid));
        let result = client::send_service_request_and_wait_for_reply("process_manager", process_manager::PROCESS_MANAGER_WAIT_FOR_PROCESS, &request_data);
        if result.is_err() {
            return Err(crate::error_kind::ErrorKind::Other.into());
        } else {
            let reply: ServiceReplyData<i32> = result.unwrap();
            let reply_message_ref: &i32 = reply.get_reply_message_ref();
            if *reply_message_ref == -1 {
                continue;
            }
            return Ok(*reply_message_ref);
        }
    }
    
}