From fb1d748a2c49597934337432a78be2a5a098ca0e Mon Sep 17 00:00:00 2001 From: Bernardo Date: Sat, 19 Jan 2019 01:15:22 +0100 Subject: actually drop watcher, use parking_lot::Mutex --- Cargo.lock | 1 + crates/ra_vfs/Cargo.toml | 1 + crates/ra_vfs/src/watcher.rs | 26 +++++++++++++++++--------- 3 files changed, 19 insertions(+), 9 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 2d18122d8..9cd0b3d9f 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1042,6 +1042,7 @@ dependencies = [ "ignore 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)", "log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)", "notify 4.0.6 (git+https://github.com/vemoo/notify/?branch=v4-legacy)", + "parking_lot 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)", "ra_arena 0.1.0", "relative-path 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", "rustc-hash 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", diff --git a/crates/ra_vfs/Cargo.toml b/crates/ra_vfs/Cargo.toml index 58196555c..b77b7139f 100644 --- a/crates/ra_vfs/Cargo.toml +++ b/crates/ra_vfs/Cargo.toml @@ -14,6 +14,7 @@ log = "0.4.6" notify = { git = "https://github.com/vemoo/notify/", branch = "v4-legacy" } ignore = "0.4" drop_bomb = "0.1.0" +parking_lot = "0.7.0" thread_worker = { path = "../thread_worker" } ra_arena = { path = "../ra_arena" } diff --git a/crates/ra_vfs/src/watcher.rs b/crates/ra_vfs/src/watcher.rs index 013611e1a..9d552f886 100644 --- a/crates/ra_vfs/src/watcher.rs +++ b/crates/ra_vfs/src/watcher.rs @@ -3,15 +3,16 @@ use crossbeam_channel::Sender; use drop_bomb::DropBomb; use ignore; use notify::{DebouncedEvent, RecommendedWatcher, RecursiveMode, Watcher as NotifyWatcher}; +use parking_lot::Mutex; use std::{ path::{Path, PathBuf}, - sync::{mpsc, Arc, Mutex}, + sync::{mpsc, Arc}, thread, time::Duration, }; pub struct Watcher { - watcher: Arc>, + watcher: Arc>>, thread: thread::JoinHandle<()>, bomb: DropBomb, } @@ -27,7 +28,7 @@ pub enum WatcherChange { fn handle_change_event( ev: DebouncedEvent, sender: &Sender, - watcher: &Arc>, + watcher: &Arc>>, ) -> Result<(), Box> { match ev { DebouncedEvent::NoticeWrite(_) @@ -69,16 +70,23 @@ fn watch_one(watcher: &mut RecommendedWatcher, path: &Path) { } } -fn watch_recursive(watcher: &Arc>, path: &Path) { +fn watch_recursive(watcher: &Arc>>, path: &Path) { log::debug!("watch_recursive \"{}\"", path.display()); - let mut w = watcher.lock().unwrap(); + let mut watcher = watcher.lock(); + let mut watcher = match *watcher { + Some(ref mut watcher) => watcher, + None => { + // watcher has been dropped + return; + } + }; // TODO it seems path itself isn't checked against ignores // check if path should be ignored before walking it for res in ignore::Walk::new(path) { match res { Ok(entry) => { if entry.path().is_dir() { - watch_one(&mut w, entry.path()); + watch_one(&mut watcher, entry.path()); } } Err(e) => log::warn!("watcher error: {}", e), @@ -91,10 +99,10 @@ impl Watcher { output_sender: Sender, ) -> Result> { let (input_sender, input_receiver) = mpsc::channel(); - let watcher = Arc::new(Mutex::new(notify::watcher( + let watcher = Arc::new(Mutex::new(Some(notify::watcher( input_sender, Duration::from_millis(250), - )?)); + )?))); let w = watcher.clone(); let thread = thread::spawn(move || { input_receiver @@ -116,7 +124,7 @@ impl Watcher { pub fn shutdown(mut self) -> thread::Result<()> { self.bomb.defuse(); - drop(self.watcher); + drop(self.watcher.lock().take()); let res = self.thread.join(); match &res { Ok(()) => log::info!("... Watcher terminated with ok"), -- cgit v1.2.3