wip: here goes the os_thread and OsContext

This commit is contained in:
denis 2021-03-18 12:20:23 +02:00 committed by Kunal Mohan
parent d8986351ed
commit daddac65aa
2 changed files with 270 additions and 178 deletions

View file

@ -1,7 +1,7 @@
//! Error context system based on a thread-local representation of the call stack, itself based on
//! the instructions that are sent between threads.
use super::{AppInstruction, ASYNCOPENCALLS, OPENCALLS};
use super::{os_input_output::OsApiInstruction, AppInstruction, OPENCALLS};
use crate::pty_bus::PtyInstruction;
use crate::screen::ScreenInstruction;
use serde::{Deserialize, Serialize};
@ -138,6 +138,8 @@ pub enum ContextType {
Screen(ScreenContext),
/// A PTY-related call.
Pty(PtyContext),
/// An OS-related call.
Os(OsContext),
/// A plugin-related call.
Plugin(PluginContext),
/// An app-related call.
@ -158,7 +160,7 @@ impl Display for ContextType {
match *self {
ContextType::Screen(c) => write!(f, "{}screen_thread: {}{:?}", purple, green, c),
ContextType::Pty(c) => write!(f, "{}pty_thread: {}{:?}", purple, green, c),
ContextType::Os(c) => write!(f, "{}os_thread: {}{:?}", purple, green, c),
ContextType::Plugin(c) => write!(f, "{}plugin_thread: {}{:?}", purple, green, c),
ContextType::App(c) => write!(f, "{}main_thread: {}{:?}", purple, green, c),
ContextType::IpcServer => write!(f, "{}ipc_server: {}AcceptInput", purple, green),
@ -293,6 +295,41 @@ impl From<&PtyInstruction> for PtyContext {
}
}
#[derive(Debug, Clone, Copy, PartialEq, Serialize, Deserialize)]
pub enum OsContext {
SpawnTerminal,
GetTerminalSizeUsingFd,
SetTerminalSizeUsingFd,
SetRawMode,
UnsetRawMode,
ReadFromTtyStdout,
WriteToTtyStdin,
TcDrain,
Kill,
ReadFromStdin,
GetStdoutWriter,
BoxClone,
}
impl From<&OsApiInstruction> for OsContext {
fn from(os_instruction: &OsApiInstruction) -> Self {
match *os_instruction {
OsApiInstruction::SpawnTerminal(_) => OsContext::SpawnTerminal,
OsApiInstruction::GetTerminalSizeUsingFd(_) => OsContext::GetTerminalSizeUsingFd,
OsApiInstruction::SetTerminalSizeUsingFd(_, _, _) => OsContext::SetTerminalSizeUsingFd,
OsApiInstruction::SetRawMode(_) => OsContext::SetRawMode,
OsApiInstruction::UnsetRawMode(_) => OsContext::UnsetRawMode,
OsApiInstruction::ReadFromTtyStdout(_, _) => OsContext::ReadFromTtyStdout,
OsApiInstruction::WriteToTtyStdin(_, _) => OsContext::WriteToTtyStdin,
OsApiInstruction::TcDrain(_) => OsContext::TcDrain,
OsApiInstruction::Kill(_) => OsContext::Kill,
OsApiInstruction::ReadFromStdin => OsContext::ReadFromStdin,
OsApiInstruction::GetStdoutWriter => OsContext::GetStdoutWriter,
OsApiInstruction::BoxClone => OsContext::BoxClone
}
}
}
// FIXME: This whole pattern *needs* a macro eventually, it's soul-crushing to write
use crate::wasm_vm::PluginInstruction;

View file

@ -3,7 +3,7 @@ use crate::common::{
ChannelWithContext, ClientInstruction, IpcSenderWithContext, SenderType, SenderWithContext,
ServerInstruction,
};
use crate::errors::{ContextType, ErrorContext, PtyContext};
use crate::errors::{ContextType, ErrorContext, OsContext, PtyContext};
use crate::os_input_output::{OsApi, OsApiInstruction};
use crate::panes::PaneId;
use crate::pty_bus::{PtyBus, PtyInstruction};
@ -30,7 +30,8 @@ pub fn start_server(os_input: Box<dyn OsApi>, opts: CliArgs) -> (thread::JoinHan
#[cfg(test)]
let (server_name, server_buffer) = SharedRingBuffer::create_temp(8192).unwrap();
let (send_os_instructions, receive_os_instructions): ChannelWithContext<OsApiInstruction> = channel();
let (send_os_instructions, receive_os_instructions): ChannelWithContext<OsApiInstruction> =
channel();
let mut send_os_instructions = SenderWithContext::new(
ErrorContext::new(),
SenderType::Sender(send_os_instructions),
@ -120,6 +121,59 @@ pub fn start_server(os_input: Box<dyn OsApi>, opts: CliArgs) -> (thread::JoinHan
})
.unwrap();
let os_thread = thread::Builder::new()
.name("os".to_string())
.spawn({
let mut os_input = os_input.clone();
move || loop {
let (event, mut err_ctx) = receive_os_instructions
.recv()
.expect("failed to receive an event on the channel");
err_ctx.add_call(ContextType::Os(OsContext::from(&event)));
match event {
OsApiInstruction::SpawnTerminal(file_to_open) => {
os_input.spawn_terminal(file_to_open);
}
OsApiInstruction::GetTerminalSizeUsingFd(fd) => {
os_input.get_terminal_size_using_fd(fd);
}
OsApiInstruction::SetTerminalSizeUsingFd(fd, cols, rows) => {
os_input.set_terminal_size_using_fd(fd, cols, rows);
}
OsApiInstruction::SetRawMode(fd) => {
os_input.set_raw_mode(fd);
}
OsApiInstruction::UnsetRawMode(fd) => {
os_input.unset_raw_mode(fd);
}
OsApiInstruction::ReadFromTtyStdout(fd, mut buf) => {
let slice = buf.as_mut_slice();
os_input.read_from_tty_stdout(fd, slice).unwrap();
}
OsApiInstruction::WriteToTtyStdin(fd, mut buf) => {
let slice = buf.as_mut_slice();
os_input.write_to_tty_stdin(fd, slice).unwrap();
}
OsApiInstruction::TcDrain(fd) => {
os_input.tcdrain(fd).unwrap();
}
OsApiInstruction::Kill(pid) => {
os_input.kill(pid).unwrap();
}
OsApiInstruction::ReadFromStdin => {
os_input.read_from_stdin();
}
OsApiInstruction::GetStdoutWriter => {
os_input.get_stdout_writer();
}
OsApiInstruction::BoxClone => {
os_input.box_clone();
}
}
}
})
.unwrap();
let join_handle = thread::Builder::new()
.name("ipc_server".to_string())
.spawn({
@ -188,6 +242,7 @@ pub fn start_server(os_input: Box<dyn OsApi>, opts: CliArgs) -> (thread::JoinHan
ServerInstruction::Exit => {
let _ = send_pty_instructions.send(PtyInstruction::Exit);
let _ = pty_thread.join();
let _ = os_thread.join();
let _ = send_client_instructions[0].send(ClientInstruction::Exit);
break;
}