inhouse pty

This commit is contained in:
stjet
2025-04-30 04:50:11 +00:00
parent 724ffbd494
commit c1afd3f33e
15 changed files with 82 additions and 15 deletions

View File

@@ -9,7 +9,7 @@ default-run = "ming"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[workspace] [workspace]
members = [ "wm", "wm/linux" ] members = [ "wm", "linux" ]
[build-dependencies] [build-dependencies]
bmp-rust = "0.5.0" bmp-rust = "0.5.0"
@@ -18,16 +18,16 @@ bitcoin_hashes = { version = "0.16.0", default-features = false }
[dependencies] [dependencies]
ming-wm-lib = { path = "ming-wm-lib" } ming-wm-lib = { path = "ming-wm-lib" }
wm = { path = "wm", optional = true } wm = { path = "wm", optional = true }
linux = { path = "linux", optional = true }
rodio = { version = "0.19.0", default-features = false, features = [ "flac", "mp3", "symphonia-vorbis", "wav" ], optional = true } rodio = { version = "0.19.0", default-features = false, features = [ "flac", "mp3", "symphonia-vorbis", "wav" ], optional = true }
rand = { version = "0.9.0", default-features = false, features = [ "small_rng" ], optional = true } rand = { version = "0.9.0", default-features = false, features = [ "small_rng" ], optional = true }
id3 = { version = "1.10.0", optional = true } id3 = { version = "1.10.0", optional = true }
mp4ameta = { version = "0.11.0", optional = true } mp4ameta = { version = "0.11.0", optional = true }
metaflac = { version = "0.2.5", optional = true } metaflac = { version = "0.2.5", optional = true }
pty-process = { version = "0.5.1", optional = true }
[features] [features]
default = [ "wm", "terminal" ] default = [ "wm", "terminal" ]
terminal = [ "pty-process" ] terminal = [ "linux" ]
audio_player = [ "id3", "mp4ameta", "metaflac", "rand", "rodio" ] audio_player = [ "id3", "mp4ameta", "metaflac", "rand", "rodio" ]
[profile.release] [profile.release]

View File

Before

Width:  |  Height:  |  Size: 70 B

After

Width:  |  Height:  |  Size: 70 B

View File

Before

Width:  |  Height:  |  Size: 250 B

After

Width:  |  Height:  |  Size: 250 B

View File

Before

Width:  |  Height:  |  Size: 250 B

After

Width:  |  Height:  |  Size: 250 B

View File

@@ -69,5 +69,10 @@ More often than not, not relying on dependencies removes unnecessary bloat and c
Expect to see more dependencies in Cargo.toml eliminated soon. Expect to see more dependencies in Cargo.toml eliminated soon.
PS: PS:
1. `rodio` is unlikely to ever be eliminated (simply because audio is *complex*), and it's optional (if the audio player is not wanted) 1. `rodio` is unlikely to ever be eliminated (simply because audio is *complex*), and it's optional (if the audio player is not wanted). The dependency which provides hashing will also not be removed as I am not a cryptographer and not (quite) stupid enough to pretend being one
2. `bmp-rust` is written by me and so isn't technically an external dependency 2. `bmp-rust` is written by me and so isn't technically an external dependency
> ### Update
> Ignoring the audio player dependencies and `bmp-rust`, the only dependencies not written by me are now `libc` for libc Rust bindings and `bitcoin-hashes` for SHA-512 password hashing (yes, I know SHA-512 is not the greatest password hash function, but it is lightweight, relatively).
>
> Prior dependencies like `termion`, `linux_framebuffer`, `pty-process`, have been removed and replaced by a me-written version in the `linux` crate. As of v1.1, the dependency removing goal has been achieved. Huzzah!

View File

@@ -0,0 +1,3 @@
## Launch on Login
To launch on user login, simply add `ming` as the last line of `~/.profile`. This should work for most shells.

View File

@@ -1,3 +1,4 @@
pub mod fb; pub mod fb;
pub mod raw; pub mod raw;
pub mod keys; pub mod keys;
pub mod pty;

55
linux/src/pty.rs Normal file
View File

@@ -0,0 +1,55 @@
use std::ptr;
use std::process::{ Command, Child };
use std::fs::File;
use std::os::fd::{ OwnedFd, FromRawFd };
use libc::openpty;
//basically the master and slave are linked? slave behaves just like normal terminal
//I don't totally get it, I guess just attach the command's stdout and stderr to ptyslave for reading?
pub struct PtyMaster {
pub file: File,
}
impl PtyMaster {
pub fn new(fd: OwnedFd) -> Self {
Self {
file: File::from(fd),
}
}
}
pub struct PtySlave {
pub file: File,
fd: OwnedFd,
}
impl PtySlave {
pub fn new(fd: OwnedFd) -> Self {
Self {
file: File::from(fd.try_clone().unwrap()),
fd,
}
}
//assume stdin is piped
pub fn attach_and_spawn(&self, command: &mut Command) -> std::io::Result<Child> {
command.stdout(self.fd.try_clone().unwrap());
command.stderr(self.fd.try_clone().unwrap());
command.spawn()
}
}
pub fn open_pty() -> Result<(PtyMaster, PtySlave), ()> {
let mut master_fd = 0;
let mut slave_fd = 0;
let result = unsafe { openpty(&mut master_fd, &mut slave_fd, ptr::null_mut(), ptr::null_mut(), ptr::null_mut()) };
if result == -1 {
Err(())
} else {
let master_fd = unsafe { OwnedFd::from_raw_fd(master_fd) };
let slave_fd = unsafe { OwnedFd::from_raw_fd(slave_fd) };
Ok((PtyMaster::new(master_fd), PtySlave::new(slave_fd)))
}
}

View File

@@ -3,12 +3,13 @@ use std::vec;
use std::sync::mpsc::{ channel, Receiver, Sender }; use std::sync::mpsc::{ channel, Receiver, Sender };
use std::thread; use std::thread;
use std::process::{ Child, Stdio }; use std::process::{ Child, Stdio };
use std::process::Command;
use std::io::{ Read, Write }; use std::io::{ Read, Write };
use std::time::Duration; use std::time::Duration;
use std::path::PathBuf; use std::path::PathBuf;
use std::fmt; use std::fmt;
use pty_process::blocking; use linux::pty::open_pty;
use ming_wm_lib::window_manager_types::{ DrawInstructions, WindowLike, WindowLikeType }; use ming_wm_lib::window_manager_types::{ DrawInstructions, WindowLike, WindowLikeType };
use ming_wm_lib::messages::{ WindowMessage, WindowMessageResponse, WindowManagerRequest, ShortcutType }; use ming_wm_lib::messages::{ WindowMessage, WindowMessageResponse, WindowManagerRequest, ShortcutType };
@@ -160,8 +161,8 @@ impl WindowLike for Terminal {
//for now, ignore //for now, ignore
// //
} else if char::from(ci) == '\t' { } else if char::from(ci) == '\t' {
//for now, ignore //for now, interpret as space
// self.process_current_line.push(b' ');
} else { } else {
self.process_current_line.push(ci); self.process_current_line.push(ci);
} }
@@ -358,11 +359,13 @@ impl Terminal {
} }
Mode::Input Mode::Input
} else { } else {
let (pty, pts) = blocking::open().unwrap(); let (pty, pts) = open_pty().unwrap();
self.running_process = Some(blocking::Command::new("sh").arg("-c").arg(&self.current_input).current_dir(&self.current_path).stdin(Stdio::piped()).spawn(pts).unwrap()); let mut cmd = Command::new("sh");
let cmd = cmd.arg("-c").arg(&self.current_input).current_dir(&self.current_path).stdin(Stdio::piped());
self.running_process = Some(pts.attach_and_spawn(cmd).unwrap());
let (tx1, rx1) = channel(); let (tx1, rx1) = channel();
thread::spawn(move || { thread::spawn(move || {
for ci in pty.bytes() { for ci in pty.file.bytes() {
if let Ok(ci) = ci { if let Ok(ci) = ci {
tx1.send(ci).unwrap(); tx1.send(ci).unwrap();
} else { } else {

View File

@@ -6,9 +6,9 @@ use std::io::{ stdin, stdout, BufReader, BufRead, Write };
use std::process::exit; use std::process::exit;
use std::env; use std::env;
use wm::linux::fb::Framebuffer; use linux::fb::Framebuffer;
use wm::linux::raw::RawStdout; use linux::raw::RawStdout;
use wm::linux::keys::{ RawStdin, Key }; use linux::keys::{ RawStdin, Key };
use wm::framebuffer::{ FramebufferWriter, FramebufferInfo }; use wm::framebuffer::{ FramebufferWriter, FramebufferInfo };
use wm::window_manager::WindowManager; use wm::window_manager::WindowManager;

View File

@@ -7,6 +7,6 @@ edition = "2021"
[dependencies] [dependencies]
ming-wm-lib = { path = "../ming-wm-lib" } ming-wm-lib = { path = "../ming-wm-lib" }
linux = { path = "linux" } linux = { path = "../linux" }
bitcoin_hashes = { version = "0.16.0", default-features = false } bitcoin_hashes = { version = "0.16.0", default-features = false }
bmp-rust = "0.5.0" bmp-rust = "0.5.0"