Let fbcond rather than inputd handle input events
This commit is contained in:
+6
-132
@@ -14,11 +14,10 @@ use std::os::unix::io::{FromRawFd, RawFd};
|
||||
|
||||
use event::{EventFlags, RawEventQueue};
|
||||
use libredox::errno::EAGAIN;
|
||||
use orbclient::{Event, EventOption};
|
||||
|
||||
use extra::io::fail;
|
||||
use libredox::call as redox;
|
||||
use libredox::flag::{self, O_RDONLY};
|
||||
use libredox::flag;
|
||||
|
||||
const _MAN_PAGE: &'static str = /* @MANSTART{getty} */
|
||||
r#"
|
||||
@@ -51,92 +50,16 @@ AUTHOR
|
||||
const DEFAULT_COLS: u32 = 80;
|
||||
const DEFAULT_LINES: u32 = 30;
|
||||
|
||||
fn process_events(ctrl: &mut bool, events: &[Event]) -> Vec<u8> {
|
||||
let mut buf = vec![];
|
||||
|
||||
for event in events.iter() {
|
||||
if let EventOption::Key(key_event) = event.to_option() {
|
||||
if key_event.scancode == 0x1D {
|
||||
*ctrl = key_event.pressed;
|
||||
} else if key_event.pressed {
|
||||
match key_event.scancode {
|
||||
0x0E => {
|
||||
// Backspace
|
||||
buf.extend_from_slice(b"\x7F");
|
||||
}
|
||||
0x47 => {
|
||||
// Home
|
||||
buf.extend_from_slice(b"\x1B[H");
|
||||
}
|
||||
0x48 => {
|
||||
// Up
|
||||
buf.extend_from_slice(b"\x1B[A");
|
||||
}
|
||||
0x49 => {
|
||||
// Page up
|
||||
buf.extend_from_slice(b"\x1B[5~");
|
||||
}
|
||||
0x4B => {
|
||||
// Left
|
||||
buf.extend_from_slice(b"\x1B[D");
|
||||
}
|
||||
0x4D => {
|
||||
// Right
|
||||
buf.extend_from_slice(b"\x1B[C");
|
||||
}
|
||||
0x4F => {
|
||||
// End
|
||||
buf.extend_from_slice(b"\x1B[F");
|
||||
}
|
||||
0x50 => {
|
||||
// Down
|
||||
buf.extend_from_slice(b"\x1B[B");
|
||||
}
|
||||
0x51 => {
|
||||
// Page down
|
||||
buf.extend_from_slice(b"\x1B[6~");
|
||||
}
|
||||
0x52 => {
|
||||
// Insert
|
||||
buf.extend_from_slice(b"\x1B[2~");
|
||||
}
|
||||
0x53 => {
|
||||
// Delete
|
||||
buf.extend_from_slice(b"\x1B[3~");
|
||||
}
|
||||
_ => {
|
||||
let c = match key_event.character {
|
||||
c @ 'A'..='Z' if *ctrl => ((c as u8 - b'A') + b'\x01') as char,
|
||||
c @ 'a'..='z' if *ctrl => ((c as u8 - b'a') + b'\x01') as char,
|
||||
c => c,
|
||||
};
|
||||
|
||||
if c != '\0' {
|
||||
let mut b = [0; 4];
|
||||
buf.extend_from_slice(c.encode_utf8(&mut b).as_bytes());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
buf
|
||||
}
|
||||
|
||||
pub fn handle(
|
||||
event_queue: &mut RawEventQueue,
|
||||
tty_fd: RawFd,
|
||||
consumer_fd: Option<RawFd>,
|
||||
master_fd: RawFd,
|
||||
process: &mut Child,
|
||||
) {
|
||||
// tty_fd => Display
|
||||
// master_fd => PTY
|
||||
// consumer_fd => Either(`input:consumer/{#VT}`, $DEVICE)
|
||||
|
||||
let mut ctrl = false;
|
||||
let mut handle_event = |event_id: usize| {
|
||||
let handle_event = |event_id: usize| {
|
||||
if event_id as RawFd == tty_fd {
|
||||
let mut packet = [0; 4096];
|
||||
loop {
|
||||
@@ -164,49 +87,12 @@ pub fn handle(
|
||||
let _ = redox::fsync(tty_fd as usize);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if let Some(consumer_fd) = consumer_fd {
|
||||
if event_id as RawFd != consumer_fd {
|
||||
println!("getty: unknown event {}", event_id);
|
||||
}
|
||||
|
||||
let mut packet = [0; 4096];
|
||||
loop {
|
||||
let count = match redox::read(consumer_fd as usize, &mut packet) {
|
||||
Ok(0) => return,
|
||||
Ok(count) => count,
|
||||
Err(ref err) if err.errno == EAGAIN => break,
|
||||
Err(_) => panic!("getty: failed to read from master TTY"),
|
||||
};
|
||||
|
||||
let events = unsafe {
|
||||
core::slice::from_raw_parts(
|
||||
packet.as_ptr() as *const Event,
|
||||
count / core::mem::size_of::<Event>(),
|
||||
)
|
||||
};
|
||||
|
||||
let buf = process_events(&mut ctrl, events);
|
||||
redox::write(master_fd as usize, buf.as_slice())
|
||||
.expect("getty: failed to write to TTY");
|
||||
|
||||
if packet[0] & 1 == 1 {
|
||||
let _ = redox::fsync(tty_fd as usize);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
println!("getty: unknown event {}", event_id);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
handle_event(tty_fd as usize);
|
||||
handle_event(master_fd as usize);
|
||||
|
||||
if let Some(consumer_fd) = consumer_fd {
|
||||
handle_event(consumer_fd as usize);
|
||||
}
|
||||
|
||||
'events: loop {
|
||||
let sys_event = event_queue
|
||||
.next()
|
||||
@@ -258,7 +144,6 @@ pub fn getpty(columns: u32, lines: u32) -> (RawFd, String) {
|
||||
|
||||
fn daemon(
|
||||
tty_fd: RawFd,
|
||||
consumer_fd: Option<RawFd>,
|
||||
clear: bool,
|
||||
contain: bool,
|
||||
stderr: &mut Stderr,
|
||||
@@ -281,12 +166,6 @@ fn daemon(
|
||||
|
||||
let mut event_queue = event::RawEventQueue::new().expect("getty: failed to open event queue");
|
||||
|
||||
if let Some(consumer_fd) = consumer_fd {
|
||||
event_queue
|
||||
.subscribe(consumer_fd as usize, 0, EventFlags::READ)
|
||||
.expect("getty: failed to fevent TTY");
|
||||
}
|
||||
|
||||
event_queue
|
||||
.subscribe(tty_fd as usize, 0, EventFlags::READ)
|
||||
.expect("getty: failed to fevent TTY");
|
||||
@@ -329,7 +208,6 @@ fn daemon(
|
||||
handle(
|
||||
&mut event_queue,
|
||||
tty_fd,
|
||||
consumer_fd,
|
||||
master_fd,
|
||||
&mut process,
|
||||
);
|
||||
@@ -358,15 +236,11 @@ pub fn main() {
|
||||
let vt = args.value_of("TTY").unwrap();
|
||||
|
||||
let buf: String;
|
||||
let (vt_path, consumer) = if vt.parse::<usize>().is_ok() {
|
||||
let consumer = redox::open(format!("input:consumer/{vt}"), O_RDONLY, 0)
|
||||
.expect("getty: failed to open consumer");
|
||||
|
||||
let vt_path = if vt.parse::<usize>().is_ok() {
|
||||
buf = format!("fbcon:{vt}");
|
||||
|
||||
(&*buf, Some(consumer as RawFd))
|
||||
&*buf
|
||||
} else {
|
||||
(vt, None)
|
||||
vt
|
||||
};
|
||||
|
||||
let tty_fd = match redox::open(
|
||||
@@ -383,7 +257,7 @@ pub fn main() {
|
||||
|
||||
redox_daemon::Daemon::new(|d| {
|
||||
d.ready().expect("getty: failed to notify ");
|
||||
daemon(tty_fd as RawFd, consumer, clear, contain, &mut stderr);
|
||||
daemon(tty_fd as RawFd, clear, contain, &mut stderr);
|
||||
std::process::exit(0);
|
||||
})
|
||||
.unwrap_or_else(|err| {
|
||||
|
||||
Reference in New Issue
Block a user