gracefully handle panics in connection_handler
This commit is contained in:
parent
af130cf56e
commit
022f01e532
42
Cargo.lock
generated
42
Cargo.lock
generated
@ -101,6 +101,7 @@ dependencies = [
|
|||||||
"anyhow",
|
"anyhow",
|
||||||
"bytemuck",
|
"bytemuck",
|
||||||
"chrono",
|
"chrono",
|
||||||
|
"futures",
|
||||||
"hyper",
|
"hyper",
|
||||||
"serde",
|
"serde",
|
||||||
"serde_json",
|
"serde_json",
|
||||||
@ -194,6 +195,20 @@ version = "1.0.7"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1"
|
checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "futures"
|
||||||
|
version = "0.3.27"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "531ac96c6ff5fd7c62263c5e3c67a603af4fcaee2e1a0ae5565ba3a11e69e549"
|
||||||
|
dependencies = [
|
||||||
|
"futures-channel",
|
||||||
|
"futures-core",
|
||||||
|
"futures-io",
|
||||||
|
"futures-sink",
|
||||||
|
"futures-task",
|
||||||
|
"futures-util",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "futures-channel"
|
name = "futures-channel"
|
||||||
version = "0.3.27"
|
version = "0.3.27"
|
||||||
@ -201,6 +216,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||||||
checksum = "164713a5a0dcc3e7b4b1ed7d3b433cabc18025386f9339346e8daf15963cf7ac"
|
checksum = "164713a5a0dcc3e7b4b1ed7d3b433cabc18025386f9339346e8daf15963cf7ac"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"futures-core",
|
"futures-core",
|
||||||
|
"futures-sink",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
@ -209,6 +225,18 @@ version = "0.3.27"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "86d7a0c1aa76363dac491de0ee99faf6941128376f1cf96f07db7603b7de69dd"
|
checksum = "86d7a0c1aa76363dac491de0ee99faf6941128376f1cf96f07db7603b7de69dd"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "futures-io"
|
||||||
|
version = "0.3.27"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "89d422fa3cbe3b40dca574ab087abb5bc98258ea57eea3fd6f1fa7162c778b91"
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "futures-sink"
|
||||||
|
version = "0.3.27"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "ec93083a4aecafb2a80a885c9de1f0ccae9dbd32c2bb54b0c3a65690e0b8d2f2"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "futures-task"
|
name = "futures-task"
|
||||||
version = "0.3.27"
|
version = "0.3.27"
|
||||||
@ -221,10 +249,15 @@ version = "0.3.27"
|
|||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "3ef6b17e481503ec85211fed8f39d1970f128935ca1f814cd32ac4a6842e84ab"
|
checksum = "3ef6b17e481503ec85211fed8f39d1970f128935ca1f814cd32ac4a6842e84ab"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
|
"futures-channel",
|
||||||
"futures-core",
|
"futures-core",
|
||||||
|
"futures-io",
|
||||||
|
"futures-sink",
|
||||||
"futures-task",
|
"futures-task",
|
||||||
|
"memchr",
|
||||||
"pin-project-lite",
|
"pin-project-lite",
|
||||||
"pin-utils",
|
"pin-utils",
|
||||||
|
"slab",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
@ -512,6 +545,15 @@ dependencies = [
|
|||||||
"serde",
|
"serde",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "slab"
|
||||||
|
version = "0.4.8"
|
||||||
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
|
checksum = "6528351c9bc8ab22353f9d776db39a20288e8d6c37ef8cfe3317cf875eecfc2d"
|
||||||
|
dependencies = [
|
||||||
|
"autocfg",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "socket2"
|
name = "socket2"
|
||||||
version = "0.4.9"
|
version = "0.4.9"
|
||||||
|
@ -13,6 +13,7 @@ serde = { version = "1.0.152", features = ["derive"] }
|
|||||||
serde_json = "1.0.91"
|
serde_json = "1.0.91"
|
||||||
hyper = { version = "0.14.24", optional = true, features = ["server", "http1", "tcp"] }
|
hyper = { version = "0.14.24", optional = true, features = ["server", "http1", "tcp"] }
|
||||||
chrono = { version = "0.4.23", optional = true }
|
chrono = { version = "0.4.23", optional = true }
|
||||||
|
futures = { version = "0.3.27", default-features = false, features = ["std"] }
|
||||||
|
|
||||||
[features]
|
[features]
|
||||||
default = ["debug_server", "chrono"]
|
default = ["debug_server", "chrono"]
|
||||||
|
44
src/main.rs
44
src/main.rs
@ -91,13 +91,6 @@ impl Config {
|
|||||||
|
|
||||||
#[tokio::main]
|
#[tokio::main]
|
||||||
async fn main() -> anyhow::Result<()> {
|
async fn main() -> anyhow::Result<()> {
|
||||||
// make whole programm exit on worker thread crash
|
|
||||||
let default_panic = std::panic::take_hook();
|
|
||||||
std::panic::set_hook(Box::new(move |info| {
|
|
||||||
default_panic(info);
|
|
||||||
std::process::exit(1);
|
|
||||||
}));
|
|
||||||
|
|
||||||
let config = Arc::new(Config::load("config.json")?);
|
let config = Arc::new(Config::load("config.json")?);
|
||||||
|
|
||||||
if config.allowed_ports.is_empty() {
|
if config.allowed_ports.is_empty() {
|
||||||
@ -127,7 +120,9 @@ async fn main() -> anyhow::Result<()> {
|
|||||||
|
|
||||||
if should_store {
|
if should_store {
|
||||||
last_store = Some(last_update);
|
last_store = Some(last_update);
|
||||||
port_handler.store(&cache_path).unwrap();
|
if let Err(err) = port_handler.store(&cache_path) {
|
||||||
|
println!("failed to store cache: {err:?}");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -152,17 +147,36 @@ async fn main() -> anyhow::Result<()> {
|
|||||||
let mut handler_metadata = HandlerMetadata::default();
|
let mut handler_metadata = HandlerMetadata::default();
|
||||||
|
|
||||||
tokio::spawn(async move {
|
tokio::spawn(async move {
|
||||||
let res =
|
use futures::future::FutureExt;
|
||||||
connection_handler(&config, &mut handler_metadata, &port_handler, &mut stream)
|
|
||||||
.await;
|
|
||||||
|
|
||||||
if let Err(err) = res {
|
let res = std::panic::AssertUnwindSafe(connection_handler(
|
||||||
println!("client at {addr} had an error: {err:?}");
|
&config,
|
||||||
|
&mut handler_metadata,
|
||||||
|
&port_handler,
|
||||||
|
&mut stream,
|
||||||
|
))
|
||||||
|
.catch_unwind()
|
||||||
|
.await;
|
||||||
|
|
||||||
|
let error = match res {
|
||||||
|
Err(err) => {
|
||||||
|
let err = err
|
||||||
|
.downcast::<String>()
|
||||||
|
.unwrap_or_else(|_| Box::new("?".to_owned()));
|
||||||
|
|
||||||
|
Some(format!("panic at: {err}"))
|
||||||
|
}
|
||||||
|
Ok(Err(err)) => Some(err.to_string()),
|
||||||
|
Ok(Ok(())) => None,
|
||||||
|
};
|
||||||
|
|
||||||
|
if let Some(err) = error {
|
||||||
|
println!("client at {addr} had an error: {err}");
|
||||||
|
|
||||||
let mut packet = Packet::default();
|
let mut packet = Packet::default();
|
||||||
|
|
||||||
packet.data.extend_from_slice(err.to_string().as_bytes());
|
packet.data.extend_from_slice(err.as_bytes());
|
||||||
packet.data.truncate(0xfe);
|
packet.data.truncate((u8::MAX - 1) as usize);
|
||||||
packet.data.push(0);
|
packet.data.push(0);
|
||||||
packet.header = Header {
|
packet.header = Header {
|
||||||
kind: PacketKind::Error.raw(),
|
kind: PacketKind::Error.raw(),
|
||||||
|
@ -198,7 +198,7 @@ impl PortHandler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn store(&self, cache: &Path) -> anyhow::Result<()> {
|
pub fn store(&self, cache: &Path) -> anyhow::Result<()> {
|
||||||
println!("storing database");
|
println!("storing cache");
|
||||||
let temp_file = cache.with_extension(".temp");
|
let temp_file = cache.with_extension(".temp");
|
||||||
|
|
||||||
serde_json::to_writer(BufWriter::new(File::create(&temp_file)?), self)?;
|
serde_json::to_writer(BufWriter::new(File::create(&temp_file)?), self)?;
|
||||||
@ -208,7 +208,7 @@ impl PortHandler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn load(cache: &Path) -> std::io::Result<Self> {
|
pub fn load(cache: &Path) -> std::io::Result<Self> {
|
||||||
println!("loading database");
|
println!("loading cache");
|
||||||
Ok(serde_json::from_reader(BufReader::new(File::open(cache)?))?)
|
Ok(serde_json::from_reader(BufReader::new(File::open(cache)?))?)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user