mirror of
https://github.com/hermitcore/libhermit.git
synced 2025-03-09 00:00:03 +01:00
More bugfixes; kill_daemon doesn't cause the client to crash anymore
This commit is contained in:
parent
18a589317f
commit
71d004d315
3 changed files with 85 additions and 26 deletions
|
@ -2,6 +2,7 @@ use std::os::unix::net::{UnixStream, UnixListener};
|
|||
use std::path::Path;
|
||||
use std::result;
|
||||
use std::thread;
|
||||
use std::process;
|
||||
use log;
|
||||
use log::{LogMetadata, LogRecord, SetLoggerError, LogLevel, LogLevelFilter};
|
||||
use nix::unistd::{fork, ForkResult};
|
||||
|
@ -57,7 +58,11 @@ impl Connection {
|
|||
pub fn connect() -> Connection {
|
||||
if !Path::new("/tmp/hermit_daemon").exists() {
|
||||
match fork() {
|
||||
Ok(ForkResult::Child) => daemon_handler(),
|
||||
Ok(ForkResult::Child) => {
|
||||
daemon_handler();
|
||||
|
||||
process::exit(0);
|
||||
},
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
|
@ -76,7 +81,21 @@ impl Connection {
|
|||
|
||||
let mut buf = Vec::new();
|
||||
|
||||
self.socket.read_to_end(&mut buf).unwrap();
|
||||
if let Err(err) = self.socket.read_to_end(&mut buf) {
|
||||
if let Action::KillDaemon = action {
|
||||
return ActionResult::KillDaemon(Ok(()));
|
||||
}
|
||||
|
||||
panic!("The daemon seem to be crashed!");
|
||||
}
|
||||
|
||||
if buf.len() == 0 {
|
||||
if let Action::KillDaemon = action {
|
||||
return ActionResult::KillDaemon(Ok(()));
|
||||
} else {
|
||||
panic!("he result was empty!");
|
||||
}
|
||||
}
|
||||
|
||||
deserialize(&buf).unwrap()
|
||||
}
|
||||
|
@ -208,7 +227,7 @@ pub fn daemon_handler() {
|
|||
//for stream in listener.incoming() {
|
||||
// match stream {
|
||||
// Ok(mut stream) => {
|
||||
loop { match listener.accept() {
|
||||
'outer: loop { match listener.accept() {
|
||||
Ok((mut stream, addr)) => {
|
||||
// loop {
|
||||
if let Ok(nread) = stream.read(&mut buf) {
|
||||
|
@ -220,7 +239,7 @@ pub fn daemon_handler() {
|
|||
let ret = match action {
|
||||
Action::KillDaemon => {
|
||||
fs::remove_file("/tmp/hermit_daemon").unwrap();
|
||||
break;
|
||||
break 'outer;
|
||||
},
|
||||
Action::CreateIsle(path, specs) => ActionResult::CreateIsle(state.create_isle(path,specs)),
|
||||
Action::List => ActionResult::List(state.list()),
|
||||
|
|
|
@ -5,6 +5,8 @@ use std::fs::File;
|
|||
use std::io::Read;
|
||||
use std::process::{ChildStdout, ChildStderr};
|
||||
use std::thread;
|
||||
use std::os::unix::net::UnixStream;
|
||||
use std::io::Write;
|
||||
|
||||
use hermit::{Isle, IsleParameterQEmu};
|
||||
use hermit::utils;
|
||||
|
@ -32,6 +34,7 @@ impl QEmu {
|
|||
let mut child = QEmu::start_with(path, mem_size, num_cpus, additional, &tmpf, &pidf)?.spawn().expect("Couldn't find qemu binary!");
|
||||
let stdout = child.stdout.take().unwrap();
|
||||
let stderr = child.stderr.take().unwrap();
|
||||
println!("{}", pidf);
|
||||
|
||||
Ok(QEmu {
|
||||
socket: Some(Socket::new_qemu()),
|
||||
|
@ -39,17 +42,18 @@ impl QEmu {
|
|||
stdout: stdout,
|
||||
stderr: stderr,
|
||||
tmp_file: tmpf,
|
||||
pid_file: pidf
|
||||
pid_file: pidf,
|
||||
})
|
||||
}
|
||||
|
||||
pub fn start_with(path: &str, mem_size: u64, num_cpus: u32, add: IsleParameterQEmu, tmp_file: &str, pid_file: &str) -> Result<Command> {
|
||||
let hostfwd = format!("user,hostfwd=tcp:127.0.0.1:{}-:{}", add.port, add.port);
|
||||
let monitor_str = format!("telnet:127.0.0.1:{},server,nowait", add.port+1);
|
||||
//let monitor_str = format!("telnet:127.0.0.1:{},server,nowait", add.port+1);
|
||||
let monitor_str = format!("unix:{}_monitor,server,nowait", pid_file);
|
||||
let chardev = format!("file,id=gnc0,path={}",&tmp_file);
|
||||
let freq = format!("\"-freq{} -proxy\"",(utils::cpufreq().unwrap()/1000).to_string());
|
||||
let num_cpus = num_cpus.to_string();
|
||||
let mem_size = mem_size.to_string();
|
||||
let mem_size = format!("{}B", mem_size);
|
||||
|
||||
let exe = env::current_exe().unwrap();
|
||||
let name = exe.to_str().unwrap();
|
||||
|
@ -86,10 +90,8 @@ impl QEmu {
|
|||
args.push("host");
|
||||
}
|
||||
|
||||
if add.monitor {
|
||||
args.push("-monitor");
|
||||
args.push(&monitor_str);
|
||||
}
|
||||
args.push("-monitor");
|
||||
args.push(&monitor_str);
|
||||
|
||||
if add.should_debug {
|
||||
args.push("-s");
|
||||
|
@ -100,14 +102,12 @@ impl QEmu {
|
|||
args.push("dump");
|
||||
}
|
||||
|
||||
debug!("Execute {} with args {:#?}", add.binary, args);
|
||||
|
||||
debug!("Execute {} with {}", add.binary, args.join(" "));
|
||||
|
||||
let mut cmd = Command::new(add.binary);
|
||||
|
||||
cmd.args(args).stdout(Stdio::piped()).stderr(Stdio::piped());
|
||||
|
||||
|
||||
Ok(cmd)
|
||||
}
|
||||
|
||||
|
@ -120,6 +120,22 @@ impl QEmu {
|
|||
|
||||
(stdout, stderr)
|
||||
}
|
||||
|
||||
pub fn send_cmd(&self, cmd: &str) -> Result<String> {
|
||||
let file = format!("{}_monitor", self.pid_file);
|
||||
|
||||
let mut control = UnixStream::connect(&file)
|
||||
.map_err(|_| Error::InvalidFile(file.clone()))?;
|
||||
|
||||
control.write_all(cmd.as_bytes())
|
||||
.map_err(|_| Error::InvalidFile(file))?;
|
||||
|
||||
let mut buf = String::new();
|
||||
|
||||
control.read_to_string(&mut buf);
|
||||
|
||||
Ok(buf)
|
||||
}
|
||||
}
|
||||
|
||||
impl Isle for QEmu {
|
||||
|
@ -155,11 +171,15 @@ impl Isle for QEmu {
|
|||
}
|
||||
|
||||
fn stop(&mut self) -> Result<i32> {
|
||||
self.send_cmd("system_powerdown")?;
|
||||
|
||||
Ok(0)
|
||||
}
|
||||
|
||||
fn is_running(&mut self) -> Result<bool> {
|
||||
Ok(true)
|
||||
let state = self.send_cmd("info status")?;
|
||||
|
||||
Ok(state == "running")
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -31,19 +31,10 @@ impl Socket {
|
|||
}
|
||||
|
||||
pub fn connect(&self) -> Socket {
|
||||
let mut stream = match *self {
|
||||
Socket::QEmu => TcpStream::connect(("127.0.0.1", 0x494E)).unwrap(),
|
||||
Socket::Multi(id) => TcpStream::connect((format!("127.0.0.{}", id).as_ref(), 0x494E)).unwrap(),
|
||||
_ => panic!("")
|
||||
};
|
||||
|
||||
debug!("Connected to {}", stream.peer_addr().unwrap());
|
||||
|
||||
// prepare the initializing struct
|
||||
let length: usize = 4 + env::args().skip(2).map(|x| 4+x.len()).sum::<usize>()+ 4 + env::vars().map(|(x,y)| 5 + x.len()+ y.len()).sum::<usize>();
|
||||
|
||||
let mut buf = Cursor::new(vec![0u8;length]);
|
||||
buf.write_u32::<LittleEndian>(HERMIT_MAGIC);
|
||||
|
||||
// send all arguments (skip first)
|
||||
buf.write_u32::<LittleEndian>(env::args().count() as u32 - 2);
|
||||
for key in env::args().skip(2) {
|
||||
|
@ -59,8 +50,37 @@ impl Socket {
|
|||
buf.write(tmp.as_bytes());
|
||||
}
|
||||
|
||||
stream.write(buf.get_ref());
|
||||
let mut stream;
|
||||
loop {
|
||||
match *self {
|
||||
Socket::QEmu => {
|
||||
match TcpStream::connect(("127.0.0.1", 0x494E)) {
|
||||
Ok(mut s) => {
|
||||
match s.write(buf.get_ref()) {
|
||||
Ok(_) => { stream = s; break; },
|
||||
Err(_) => {}
|
||||
}
|
||||
},
|
||||
|
||||
Err(_) => {}
|
||||
}
|
||||
},
|
||||
Socket::Multi(id) => {
|
||||
match TcpStream::connect((format!("127.0.0.{}", id).as_ref(), 0x494E)) {
|
||||
Ok(mut s) => {
|
||||
match s.write(buf.get_ref()) {
|
||||
Ok(_) => { stream = s; break; },
|
||||
Err(_) => {}
|
||||
}
|
||||
},
|
||||
Err(_) => {}
|
||||
}
|
||||
},
|
||||
_ => panic!("")
|
||||
}
|
||||
}
|
||||
|
||||
debug!("Connected to {}", stream.peer_addr().unwrap());
|
||||
debug!("Transmitted environment and arguments with length {}", length);
|
||||
|
||||
Socket::Connected { stream: stream, stdout: String::new(), stderr: String::new() }
|
||||
|
|
Loading…
Add table
Reference in a new issue