Bugfix/backup lock (#1093)

* add write lock before getting model

* update compat cargo.lock file

* update encryptfs passphrase cmd

* add additional safeguards around dropping stdin handles

* proper lock ordering for server status
This commit is contained in:
Lucy C
2022-01-21 10:53:59 -07:00
committed by Aiden McClelland
parent 5d9f7e412c
commit 5b87aca298
5 changed files with 40 additions and 32 deletions

View File

@@ -109,6 +109,9 @@ impl DockerAction {
.write_all(input) .write_all(input)
.await .await
.with_kind(crate::ErrorKind::Docker)?; .with_kind(crate::ErrorKind::Docker)?;
stdin.flush().await?;
stdin.shutdown().await?;
drop(stdin);
} }
enum Race<T> { enum Race<T> {
Done(T), Done(T),

View File

@@ -133,7 +133,14 @@ pub async fn backup_all(
} }
let revision = assure_backing_up(&mut db).await?; let revision = assure_backing_up(&mut db).await?;
tokio::task::spawn(async move { tokio::task::spawn(async move {
match perform_backup(&ctx, &mut db, backup_guard).await { let backup_res = perform_backup(&ctx, &mut db, backup_guard).await;
let status_model = crate::db::DatabaseModel::new().server_info().status();
status_model
.clone()
.lock(&mut db, LockType::Write)
.await
.expect("failed to lock server status");
match backup_res {
Ok(report) if report.iter().all(|(_, rep)| rep.error.is_none()) => ctx Ok(report) if report.iter().all(|(_, rep)| rep.error.is_none()) => ctx
.notification_manager .notification_manager
.notify( .notify(
@@ -195,9 +202,7 @@ pub async fn backup_all(
.expect("failed to send notification"); .expect("failed to send notification");
} }
} }
crate::db::DatabaseModel::new() status_model
.server_info()
.status()
.put(&mut db, &ServerStatus::Running) .put(&mut db, &ServerStatus::Running)
.await .await
.expect("failed to change server status"); .expect("failed to change server status");
@@ -268,6 +273,7 @@ async fn perform_backup<Db: DbHandle>(
let main_status_model = installed_model.clone().status().main(); let main_status_model = installed_model.clone().status().main();
let mut tx = db.begin().await?; // for lock scope let mut tx = db.begin().await?; // for lock scope
main_status_model.lock(&mut tx, LockType::Write).await?;
let (started, health) = match main_status_model.get(&mut tx, true).await?.into_owned() { let (started, health) = match main_status_model.get(&mut tx, true).await?.into_owned() {
MainStatus::Starting => (Some(Utc::now()), Default::default()), MainStatus::Starting => (Some(Utc::now()), Default::default()),
MainStatus::Running { started, health } => (Some(started), health.clone()), MainStatus::Running { started, health } => (Some(started), health.clone()),

View File

@@ -23,8 +23,8 @@ pub async fn mount_ecryptfs<P0: AsRef<Path>, P1: AsRef<Path>>(
.arg(src.as_ref()) .arg(src.as_ref())
.arg(dst.as_ref()) .arg(dst.as_ref())
.arg("-o") .arg("-o")
// for more information `man ecryptfs` // for more information `man ecryptfs`
.arg(format!("key=passphrase,passwd={},ecryptfs_cipher=aes,ecryptfs_key_bytes=32,ecryptfs_passthrough=n,ecryptfs_enable_filename_crypto=y", key)) .arg(format!("key=passphrase:passphrase_passwd={},ecryptfs_cipher=aes,ecryptfs_key_bytes=32,ecryptfs_passthrough=n,ecryptfs_enable_filename_crypto=y", key))
.stdin(std::process::Stdio::piped()) .stdin(std::process::Stdio::piped())
.stderr(std::process::Stdio::piped()) .stderr(std::process::Stdio::piped())
.spawn()?; .spawn()?;

View File

@@ -426,7 +426,7 @@ impl Manager {
} }
Ok(()) Ok(())
} }
/// this will depend on locks to main status. if you hold any locks when calling this function that conflict, this will deadlock
pub async fn synchronize(&self) { pub async fn synchronize(&self) {
self.shared.synchronize_now.notify_waiters(); self.shared.synchronize_now.notify_waiters();
self.shared.synchronized.notified().await self.shared.synchronized.notified().await

View File

@@ -309,7 +309,7 @@ dependencies = [
"serde_json", "serde_json",
"serde_urlencoded", "serde_urlencoded",
"thiserror", "thiserror",
"tokio 1.12.0", "tokio 1.15.0",
"tokio-util", "tokio-util",
"url", "url",
"winapi", "winapi",
@@ -920,7 +920,7 @@ dependencies = [
"stderrlog", "stderrlog",
"tar", "tar",
"thiserror", "thiserror",
"tokio 1.12.0", "tokio 1.15.0",
"tokio-compat-02", "tokio-compat-02",
"tokio-stream", "tokio-stream",
"tokio-tar", "tokio-tar",
@@ -1284,7 +1284,7 @@ dependencies = [
"http", "http",
"indexmap", "indexmap",
"slab", "slab",
"tokio 1.12.0", "tokio 1.15.0",
"tokio-util", "tokio-util",
"tracing", "tracing",
] ]
@@ -1405,7 +1405,7 @@ dependencies = [
"itoa", "itoa",
"pin-project-lite 0.2.7", "pin-project-lite 0.2.7",
"socket2", "socket2",
"tokio 1.12.0", "tokio 1.15.0",
"tower-service", "tower-service",
"tracing", "tracing",
"want", "want",
@@ -1420,7 +1420,7 @@ dependencies = [
"bytes 1.1.0", "bytes 1.1.0",
"hyper", "hyper",
"native-tls", "native-tls",
"tokio 1.12.0", "tokio 1.15.0",
"tokio-native-tls", "tokio-native-tls",
] ]
@@ -1436,7 +1436,7 @@ dependencies = [
"hyper", "hyper",
"log", "log",
"sha-1 0.9.8", "sha-1 0.9.8",
"tokio 1.12.0", "tokio 1.15.0",
"tokio-tungstenite", "tokio-tungstenite",
] ]
@@ -1450,7 +1450,7 @@ dependencies = [
"hex", "hex",
"hyper", "hyper",
"pin-project", "pin-project",
"tokio 1.12.0", "tokio 1.15.0",
] ]
[[package]] [[package]]
@@ -2138,7 +2138,7 @@ dependencies = [
"serde_cbor 0.11.1", "serde_cbor 0.11.1",
"serde_json", "serde_json",
"thiserror", "thiserror",
"tokio 1.12.0", "tokio 1.15.0",
"tracing", "tracing",
"tracing-error", "tracing-error",
] ]
@@ -2658,7 +2658,7 @@ dependencies = [
"serde_json", "serde_json",
"serde_urlencoded", "serde_urlencoded",
"time 0.2.27", "time 0.2.27",
"tokio 1.12.0", "tokio 1.15.0",
"tokio-native-tls", "tokio-native-tls",
"tokio-socks", "tokio-socks",
"url", "url",
@@ -2720,7 +2720,7 @@ dependencies = [
"serde_cbor 0.11.2", "serde_cbor 0.11.2",
"serde_json", "serde_json",
"thiserror", "thiserror",
"tokio 1.12.0", "tokio 1.15.0",
"url", "url",
"yajrc", "yajrc",
] ]
@@ -3248,7 +3248,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "14302b678d9c76b28f2e60115211e25e0aabc938269991745a169753dc00e35c" checksum = "14302b678d9c76b28f2e60115211e25e0aabc938269991745a169753dc00e35c"
dependencies = [ dependencies = [
"once_cell", "once_cell",
"tokio 1.12.0", "tokio 1.15.0",
"tokio-rustls", "tokio-rustls",
] ]
@@ -3601,11 +3601,10 @@ dependencies = [
[[package]] [[package]]
name = "tokio" name = "tokio"
version = "1.12.0" version = "1.15.0"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c2c2416fdedca8443ae44b4527de1ea633af61d8f7169ffa6e72c5b53d24efcc" checksum = "fbbf1c778ec206785635ce8ad57fe52b3009ae9e0c9f574a728f3049d3e55838"
dependencies = [ dependencies = [
"autocfg",
"bytes 1.1.0", "bytes 1.1.0",
"libc", "libc",
"memchr", "memchr",
@@ -3629,15 +3628,15 @@ dependencies = [
"once_cell", "once_cell",
"pin-project-lite 0.2.7", "pin-project-lite 0.2.7",
"tokio 0.2.25", "tokio 0.2.25",
"tokio 1.12.0", "tokio 1.15.0",
"tokio-stream", "tokio-stream",
] ]
[[package]] [[package]]
name = "tokio-macros" name = "tokio-macros"
version = "1.3.0" version = "1.7.0"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "54473be61f4ebe4efd09cec9bd5d16fa51d70ea0192213d754d2d500457db110" checksum = "b557f72f448c511a979e2564e55d74e6c4432fc96ff4f6241bc6bded342643b7"
dependencies = [ dependencies = [
"proc-macro2 1.0.29", "proc-macro2 1.0.29",
"quote 1.0.9", "quote 1.0.9",
@@ -3651,7 +3650,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f7d995660bd2b7f8c1568414c1126076c13fbb725c40112dc0120b78eb9b717b" checksum = "f7d995660bd2b7f8c1568414c1126076c13fbb725c40112dc0120b78eb9b717b"
dependencies = [ dependencies = [
"native-tls", "native-tls",
"tokio 1.12.0", "tokio 1.15.0",
] ]
[[package]] [[package]]
@@ -3661,7 +3660,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bc6844de72e57df1980054b38be3a9f4702aba4858be64dd700181a8a6d0e1b6" checksum = "bc6844de72e57df1980054b38be3a9f4702aba4858be64dd700181a8a6d0e1b6"
dependencies = [ dependencies = [
"rustls", "rustls",
"tokio 1.12.0", "tokio 1.15.0",
"webpki", "webpki",
] ]
@@ -3674,7 +3673,7 @@ dependencies = [
"either", "either",
"futures-util", "futures-util",
"thiserror", "thiserror",
"tokio 1.12.0", "tokio 1.15.0",
] ]
[[package]] [[package]]
@@ -3685,7 +3684,7 @@ checksum = "7b2f3f698253f03119ac0102beaa64f67a67e08074d03a22d18784104543727f"
dependencies = [ dependencies = [
"futures-core", "futures-core",
"pin-project-lite 0.2.7", "pin-project-lite 0.2.7",
"tokio 1.12.0", "tokio 1.15.0",
"tokio-util", "tokio-util",
] ]
@@ -3698,7 +3697,7 @@ dependencies = [
"futures-core", "futures-core",
"libc", "libc",
"redox_syscall 0.2.10", "redox_syscall 0.2.10",
"tokio 1.12.0", "tokio 1.15.0",
"tokio-stream", "tokio-stream",
"xattr", "xattr",
] ]
@@ -3712,7 +3711,7 @@ dependencies = [
"futures-util", "futures-util",
"log", "log",
"pin-project", "pin-project",
"tokio 1.12.0", "tokio 1.15.0",
"tungstenite", "tungstenite",
] ]
@@ -3727,7 +3726,7 @@ dependencies = [
"futures-sink", "futures-sink",
"log", "log",
"pin-project-lite 0.2.7", "pin-project-lite 0.2.7",
"tokio 1.12.0", "tokio 1.15.0",
] ]
[[package]] [[package]]
@@ -3756,7 +3755,7 @@ dependencies = [
"serde_derive", "serde_derive",
"sha2", "sha2",
"sha3", "sha3",
"tokio 1.12.0", "tokio 1.15.0",
] ]
[[package]] [[package]]