console: Fix crash if debug console disabled

The logic for the debug console meant that if the debug console was
_disabled_, the agent was guaranteed to crash on function exit due to
the unsafe code block. Fixed by simplifying the code to use the standard
`Option` idiom for optional values.

Fixes: #554.

Signed-off-by: James O. D. Hunt <james.o.hunt@intel.com>
This commit is contained in:
James O. D. Hunt 2020-08-21 11:40:19 +01:00
parent 572de288f0
commit d12f920b3f

View File

@ -47,7 +47,7 @@ use std::os::unix::io::AsRawFd;
use std::path::Path; use std::path::Path;
use std::sync::mpsc::{self, Sender}; use std::sync::mpsc::{self, Sender};
use std::sync::{Arc, Mutex, RwLock}; use std::sync::{Arc, Mutex, RwLock};
use std::{io, thread}; use std::{io, thread, thread::JoinHandle};
use unistd::Pid; use unistd::Pid;
mod config; mod config;
@ -84,8 +84,6 @@ lazy_static! {
Arc::new(RwLock::new(config::agentConfig::new())); Arc::new(RwLock::new(config::agentConfig::new()));
} }
use std::mem::MaybeUninit;
fn announce(logger: &Logger, config: &agentConfig) { fn announce(logger: &Logger, config: &agentConfig) {
let commit = match env::var("VERSION_COMMIT") { let commit = match env::var("VERSION_COMMIT") {
Ok(s) => s, Ok(s) => s,
@ -195,21 +193,25 @@ fn main() -> Result<()> {
// which is required to satisfy the the lifetime constraints of the auto-generated gRPC code. // which is required to satisfy the the lifetime constraints of the auto-generated gRPC code.
let _guard = slog_scope::set_global_logger(logger.new(o!("subsystem" => "rpc"))); let _guard = slog_scope::set_global_logger(logger.new(o!("subsystem" => "rpc")));
start_sandbox(&logger, &config)?; start_sandbox(&logger, &config, init_mode)?;
let _ = log_handle.join(); let _ = log_handle.join();
Ok(()) Ok(())
} }
fn start_sandbox(logger: &Logger, config: &agentConfig) -> Result<()> { fn start_sandbox(logger: &Logger, config: &agentConfig, init_mode: bool) -> Result<()> {
let shells = SHELLS.clone(); let shells = SHELLS.clone();
let debug_console_vport = config.debug_console_vport as u32; let debug_console_vport = config.debug_console_vport as u32;
let shell_handle = if config.debug_console { let mut shell_handle: Option<JoinHandle<()>> = None;
if config.debug_console {
let thread_logger = logger.clone(); let thread_logger = logger.clone();
thread::spawn(move || { let builder = thread::Builder::new();
let handle = builder
.spawn(move || {
let shells = shells.lock().unwrap(); let shells = shells.lock().unwrap();
let result = setup_debug_console(shells.to_vec(), debug_console_vport); let result = setup_debug_console(shells.to_vec(), debug_console_vport);
if result.is_err() { if result.is_err() {
@ -218,9 +220,10 @@ fn start_sandbox(logger: &Logger, config: &agentConfig) -> Result<()> {
"error" => format!("{}", result.unwrap_err())); "error" => format!("{}", result.unwrap_err()));
} }
}) })
} else { .map_err(|e| format!("{:?}", e))?;
unsafe { MaybeUninit::zeroed().assume_init() }
}; shell_handle = Some(handle);
}
// Initialize unique sandbox structure. // Initialize unique sandbox structure.
let mut s = Sandbox::new(&logger).map_err(|e| { let mut s = Sandbox::new(&logger).map_err(|e| {
@ -252,8 +255,8 @@ fn start_sandbox(logger: &Logger, config: &agentConfig) -> Result<()> {
server.shutdown(); server.shutdown();
if config.debug_console { if let Some(handle) = shell_handle {
shell_handle.join().unwrap(); handle.join().map_err(|e| format!("{:?}", e))?;
} }
Ok(()) Ok(())