commit 16f8738bffd2fedc0c54fe665f91852dfb5a80b4 Author: Jeremy Soller Date: Tue Jan 2 21:51:52 2018 -0700 Initial commit diff --git a/Cargo.lock b/Cargo.lock new file mode 100644 index 0000000000..cce61a7152 --- /dev/null +++ b/Cargo.lock @@ -0,0 +1,101 @@ +[[package]] +name = "chrono" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "num 0.1.41 (registry+https://github.com/rust-lang/crates.io-index)", + "time 0.1.38 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "kernel32-sys" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", + "winapi-build 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "libc" +version = "0.2.34" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "logd" +version = "0.1.0" +dependencies = [ + "chrono 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", + "redox_syscall 0.1.33 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "num" +version = "0.1.41" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "num-integer 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)", + "num-iter 0.1.34 (registry+https://github.com/rust-lang/crates.io-index)", + "num-traits 0.1.41 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "num-integer" +version = "0.1.35" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "num-traits 0.1.41 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "num-iter" +version = "0.1.34" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "num-integer 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)", + "num-traits 0.1.41 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "num-traits" +version = "0.1.41" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "redox_syscall" +version = "0.1.33" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "time" +version = "0.1.38" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "kernel32-sys 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", + "libc 0.2.34 (registry+https://github.com/rust-lang/crates.io-index)", + "redox_syscall 0.1.33 (registry+https://github.com/rust-lang/crates.io-index)", + "winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "winapi" +version = "0.2.8" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[[package]] +name = "winapi-build" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" + +[metadata] +"checksum chrono 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "7c20ebe0b2b08b0aeddba49c609fe7957ba2e33449882cb186a180bc60682fa9" +"checksum kernel32-sys 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "7507624b29483431c0ba2d82aece8ca6cdba9382bff4ddd0f7490560c056098d" +"checksum libc 0.2.34 (registry+https://github.com/rust-lang/crates.io-index)" = "36fbc8a8929c632868295d0178dd8f63fc423fd7537ad0738372bd010b3ac9b0" +"checksum num 0.1.41 (registry+https://github.com/rust-lang/crates.io-index)" = "cc4083e14b542ea3eb9b5f33ff48bd373a92d78687e74f4cc0a30caeb754f0ca" +"checksum num-integer 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)" = "d1452e8b06e448a07f0e6ebb0bb1d92b8890eea63288c0b627331d53514d0fba" +"checksum num-iter 0.1.34 (registry+https://github.com/rust-lang/crates.io-index)" = "7485fcc84f85b4ecd0ea527b14189281cf27d60e583ae65ebc9c088b13dffe01" +"checksum num-traits 0.1.41 (registry+https://github.com/rust-lang/crates.io-index)" = "cacfcab5eb48250ee7d0c7896b51a2c5eec99c1feea5f32025635f5ae4b00070" +"checksum redox_syscall 0.1.33 (registry+https://github.com/rust-lang/crates.io-index)" = "07b8f011e3254d5a9b318fde596d409a0001c9ae4c6e7907520c2eaa4d988c99" +"checksum time 0.1.38 (registry+https://github.com/rust-lang/crates.io-index)" = "d5d788d3aa77bc0ef3e9621256885555368b47bd495c13dd2e7413c89f845520" +"checksum winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)" = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a" +"checksum winapi-build 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc" diff --git a/Cargo.toml b/Cargo.toml new file mode 100644 index 0000000000..254793e59a --- /dev/null +++ b/Cargo.toml @@ -0,0 +1,8 @@ +[package] +name = "logd" +version = "0.1.0" +authors = ["Jeremy Soller "] + +[dependencies] +chrono = "0.4" +redox_syscall = "0.1" diff --git a/src/main.rs b/src/main.rs new file mode 100644 index 0000000000..23075de782 --- /dev/null +++ b/src/main.rs @@ -0,0 +1,28 @@ +extern crate chrono; +extern crate syscall; + +use syscall::data::Packet; +use syscall::scheme::SchemeMut; +use std::fs::File; +use std::io::{Read, Write}; +use scheme::LogScheme; + +mod scheme; + +fn main() { + if unsafe { syscall::clone(0).unwrap() } == 0 { + let mut socket = File::create(":log").expect("logd: failed to create log scheme"); + let mut scheme = LogScheme::new(); + + syscall::setrens(0, 0).expect("logd: failed to enter null namespace"); + + loop { + let mut packet = Packet::default(); + socket.read(&mut packet).expect("logd: failed to read events from log scheme"); + + scheme.handle(&mut packet); + + socket.write(&packet).expect("logd: failed to write responses to log scheme"); + } + } +} diff --git a/src/scheme.rs b/src/scheme.rs new file mode 100644 index 0000000000..424e410824 --- /dev/null +++ b/src/scheme.rs @@ -0,0 +1,124 @@ +use chrono::Local; +use std::collections::BTreeMap; +use std::io::{self, Write}; +use syscall::error::*; +use syscall::scheme::SchemeMut; + +pub struct LogHandle { + context: Box<[u8]>, + buf: Vec, +} + +pub struct LogScheme { + next_id: usize, + handles: BTreeMap, +} + +impl LogScheme { + pub fn new() -> Self { + LogScheme { + next_id: 0, + handles: BTreeMap::new(), + } + } +} + +impl SchemeMut for LogScheme { + fn open(&mut self, path: &[u8], _flags: usize, _uid: u32, _gid: u32) -> Result { + let id = self.next_id; + self.next_id += 1; + + self.handles.insert(id, LogHandle { + context: path.to_vec().into_boxed_slice(), + buf: Vec::new() + }); + + Ok(id) + } + + fn dup(&mut self, _id: usize, buf: &[u8]) -> Result { + if ! buf.is_empty() { + return Err(Error::new(EINVAL)); + } + + Ok(0) + } + + fn read(&mut self, id: usize, _buf: &mut [u8]) -> Result { + let _handle = self.handles.get(&id).ok_or(Error::new(EBADF))?; + + // TODO + + Ok(0) + } + + fn write(&mut self, id: usize, buf: &[u8]) -> Result { + let handle = self.handles.get_mut(&id).ok_or(Error::new(EBADF))?; + + let mut stdout = io::stdout(); + + let mut i = 0; + while i < buf.len() { + let b = buf[i]; + + if handle.buf.is_empty() { + let timestamp = Local::now(); + let _ = write!(handle.buf, "{}", timestamp.format("%F %T.%f")); + handle.buf.extend_from_slice(&handle.context); + handle.buf.extend_from_slice(b": "); + } + + handle.buf.push(b); + + if b == b'\n' { + let _ = stdout.write(&handle.buf); + let _ = stdout.flush(); + + handle.buf.clear(); + } + + i += 1; + } + + Ok(i) + } + + fn fcntl(&mut self, id: usize, _cmd: usize, _arg: usize) -> Result { + let _handle = self.handles.get(&id).ok_or(Error::new(EBADF))?; + + Ok(0) + } + + fn fpath(&mut self, id: usize, buf: &mut [u8]) -> Result { + let handle = self.handles.get(&id).ok_or(Error::new(EBADF))?; + + let scheme_path = b"log:"; + + let mut i = 0; + while i < buf.len() && i < scheme_path.len() { + buf[i] = scheme_path[i]; + i += 1; + } + + let mut j = 0; + while i < buf.len() && j < handle.context.len() { + buf[i] = handle.context[j]; + i += 1; + j += 1; + } + + Ok(i) + } + + fn fsync(&mut self, id: usize) -> Result { + let _handle = self.handles.get(&id).ok_or(Error::new(EBADF))?; + + Ok(0) + } + + fn close(&mut self, id: usize) -> Result { + self.handles.remove(&id).ok_or(Error::new(EBADF))?; + + Ok(0) + } +}