@@ -1137,7 +1137,7 @@ version = "2.1.3"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "09f7e37c0ed80b2a977691c47dae8625cfb21e205827106c64f7c588766b2e50"
 dependencies = [
- "async-lock",
+ "async-lock 3.4.1",
  "blocking",
  "futures-lite 2.6.0",
 ]
@@ -1151,7 +1151,7 @@ dependencies = [
  "async-channel 2.3.1",
  "async-executor",
  "async-io",
- "async-lock",
+ "async-lock 3.4.1",
  "blocking",
  "futures-lite 2.6.0",
  "once_cell",
@@ -1163,7 +1163,7 @@ version = "2.5.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "19634d6336019ef220f09fd31168ce5c184b295cbf80345437cc36094ef223ca"
 dependencies = [
- "async-lock",
+ "async-lock 3.4.1",
  "cfg-if",
  "concurrent-queue",
  "futures-io",
@@ -1175,6 +1175,15 @@ dependencies = [
  "windows-sys 0.60.2",
 ]
 
+[[package]]
+name = "async-lock"
+version = "2.8.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "287272293e9d8c41773cec55e365490fe034813a2f172f502d6ddcf75b2f582b"
+dependencies = [
+ "event-listener 2.5.3",
+]
+
 [[package]]
 name = "async-lock"
 version = "3.4.1"
@@ -1214,7 +1223,7 @@ checksum = "63255f1dc2381611000436537bbedfe83183faa303a5a0edaf191edef06526bb"
 dependencies = [
  "async-channel 2.3.1",
  "async-io",
- "async-lock",
+ "async-lock 3.4.1",
  "async-signal",
  "async-task",
  "blocking",
@@ -1243,7 +1252,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "637e00349800c0bdf8bfc21ebbc0b6524abea702b0da4168ac00d070d0c0b9f3"
 dependencies = [
  "async-io",
- "async-lock",
+ "async-lock 3.4.1",
  "atomic-waker",
  "cfg-if",
  "futures-core",
@@ -1264,7 +1273,7 @@ dependencies = [
  "async-channel 1.9.0",
  "async-global-executor",
  "async-io",
- "async-lock",
+ "async-lock 3.4.1",
  "async-process",
  "crossbeam-utils",
  "futures-channel",
@@ -9036,7 +9045,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "fc2f4eb4bc735547cfed7c0a4922cbd04a4655978c09b54f1f7b228750664c34"
 dependencies = [
  "cfg-if",
- "windows-targets 0.48.5",
+ "windows-targets 0.52.6",
 ]
 
 [[package]]
@@ -10736,7 +10745,7 @@ dependencies = [
  "ashpd 0.12.0",
  "async-fs",
  "async-io",
- "async-lock",
+ "async-lock 3.4.1",
  "blocking",
  "cbc",
  "cipher",
@@ -14823,7 +14832,7 @@ dependencies = [
  "async-executor",
  "async-fs",
  "async-io",
- "async-lock",
+ "async-lock 3.4.1",
  "async-net",
  "async-process",
  "blocking",
@@ -19868,6 +19877,7 @@ name = "worktree"
 version = "0.1.0"
 dependencies = [
  "anyhow",
+ "async-lock 2.8.0",
  "clock",
  "collections",
  "fs",
@@ -20163,7 +20173,7 @@ dependencies = [
  "async-broadcast",
  "async-executor",
  "async-io",
- "async-lock",
+ "async-lock 3.4.1",
  "async-process",
  "async-recursion",
  "async-task",
  
  
  
    
    @@ -64,7 +64,7 @@ use std::{
 use sum_tree::{Bias, Dimensions, Edit, KeyedItem, SeekTarget, SumTree, Summary, TreeMap, TreeSet};
 use text::{LineEnding, Rope};
 use util::{
-    ResultExt, debug_panic,
+    ResultExt, debug_panic, maybe,
     paths::{PathMatcher, PathStyle, SanitizedPath, home_dir},
     rel_path::RelPath,
 };
@@ -226,7 +226,7 @@ impl Default for WorkDirectory {
     }
 }
 
-#[derive(Debug, Clone)]
+#[derive(Clone)]
 pub struct LocalSnapshot {
     snapshot: Snapshot,
     global_gitignore: Option<Arc<Gitignore>>,
@@ -239,6 +239,7 @@ pub struct LocalSnapshot {
     /// The file handle of the worktree root. `None` if the worktree is a directory.
     /// (so we can find it after it's been moved)
     root_file_handle: Option<Arc<dyn fs::FileHandle>>,
+    executor: BackgroundExecutor,
 }
 
 struct BackgroundScannerState {
@@ -321,7 +322,6 @@ impl DerefMut for LocalSnapshot {
     }
 }
 
-#[derive(Debug)]
 enum ScanState {
     Started,
     Updated {
@@ -402,6 +402,7 @@ impl Worktree {
                     PathStyle::local(),
                 ),
                 root_file_handle,
+                executor: cx.background_executor().clone(),
             };
 
             let worktree_id = snapshot.id();
@@ -1069,7 +1070,7 @@ impl LocalWorktree {
                     scan_requests_rx,
                     path_prefixes_to_scan_rx,
                     next_entry_id,
-                    state: Mutex::new(BackgroundScannerState {
+                    state: async_lock::Mutex::new(BackgroundScannerState {
                         prev_snapshot: snapshot.snapshot.clone(),
                         snapshot,
                         scanned_dirs: Default::default(),
@@ -2441,7 +2442,7 @@ impl LocalSnapshot {
     fn insert_entry(&mut self, mut entry: Entry, fs: &dyn Fs) -> Entry {
         if entry.is_file() && entry.path.file_name() == Some(&GITIGNORE) {
             let abs_path = self.absolutize(&entry.path);
-            match smol::block_on(build_gitignore(&abs_path, fs)) {
+            match self.executor.block(build_gitignore(&abs_path, fs)) {
                 Ok(ignore) => {
                     self.ignores_by_parent_abs_path
                         .insert(abs_path.parent().unwrap().into(), (Arc::new(ignore), true));
@@ -2492,7 +2493,12 @@ impl LocalSnapshot {
         inodes
     }
 
-    fn ignore_stack_for_abs_path(&self, abs_path: &Path, is_dir: bool, fs: &dyn Fs) -> IgnoreStack {
+    async fn ignore_stack_for_abs_path(
+        &self,
+        abs_path: &Path,
+        is_dir: bool,
+        fs: &dyn Fs,
+    ) -> IgnoreStack {
         let mut new_ignores = Vec::new();
         let mut repo_root = None;
         for (index, ancestor) in abs_path.ancestors().enumerate() {
@@ -2503,9 +2509,8 @@ impl LocalSnapshot {
                     new_ignores.push((ancestor, None));
                 }
             }
-            let metadata = smol::block_on(fs.metadata(&ancestor.join(DOT_GIT)))
-                .ok()
-                .flatten();
+
+            let metadata = fs.metadata(&ancestor.join(DOT_GIT)).await.ok().flatten();
             if metadata.is_some() {
                 repo_root = Some(Arc::from(ancestor));
                 break;
@@ -2651,7 +2656,7 @@ impl BackgroundScannerState {
                 .any(|p| entry.path.starts_with(p))
     }
 
-    fn enqueue_scan_dir(
+    async fn enqueue_scan_dir(
         &self,
         abs_path: Arc<Path>,
         entry: &Entry,
@@ -2659,7 +2664,10 @@ impl BackgroundScannerState {
         fs: &dyn Fs,
     ) {
         let path = entry.path.clone();
-        let ignore_stack = self.snapshot.ignore_stack_for_abs_path(&abs_path, true, fs);
+        let ignore_stack = self
+            .snapshot
+            .ignore_stack_for_abs_path(&abs_path, true, fs)
+            .await;
         let mut ancestor_inodes = self.snapshot.ancestor_inodes_for_path(&path);
 
         if !ancestor_inodes.contains(&entry.inode) {
@@ -2697,11 +2705,17 @@ impl BackgroundScannerState {
         }
     }
 
-    fn insert_entry(&mut self, mut entry: Entry, fs: &dyn Fs, watcher: &dyn Watcher) -> Entry {
+    async fn insert_entry(
+        &mut self,
+        mut entry: Entry,
+        fs: &dyn Fs,
+        watcher: &dyn Watcher,
+    ) -> Entry {
         self.reuse_entry_id(&mut entry);
         let entry = self.snapshot.insert_entry(entry, fs);
         if entry.path.file_name() == Some(&DOT_GIT) {
-            self.insert_git_repository(entry.path.clone(), fs, watcher);
+            self.insert_git_repository(entry.path.clone(), fs, watcher)
+                .await;
         }
 
         #[cfg(test)]
@@ -2832,7 +2846,7 @@ impl BackgroundScannerState {
         self.snapshot.check_invariants(false);
     }
 
-    fn insert_git_repository(
+    async fn insert_git_repository(
         &mut self,
         dot_git_path: Arc<RelPath>,
         fs: &dyn Fs,
@@ -2873,10 +2887,11 @@ impl BackgroundScannerState {
             fs,
             watcher,
         )
+        .await
         .log_err();
     }
 
-    fn insert_git_repository_for_path(
+    async fn insert_git_repository_for_path(
         &mut self,
         work_directory: WorkDirectory,
         dot_git_abs_path: Arc<Path>,
@@ -2898,7 +2913,7 @@ impl BackgroundScannerState {
         let work_directory_abs_path = self.snapshot.work_directory_abs_path(&work_directory);
 
         let (repository_dir_abs_path, common_dir_abs_path) =
-            discover_git_paths(&dot_git_abs_path, fs);
+            discover_git_paths(&dot_git_abs_path, fs).await;
         watcher
             .add(&common_dir_abs_path)
             .context("failed to add common directory to watcher")
@@ -3542,7 +3557,7 @@ impl<'a> sum_tree::Dimension<'a, EntrySummary> for PathKey {
 }
 
 struct BackgroundScanner {
-    state: Mutex<BackgroundScannerState>,
+    state: async_lock::Mutex<BackgroundScannerState>,
     fs: Arc<dyn Fs>,
     fs_case_sensitive: bool,
     status_updates_tx: UnboundedSender<ScanState>,
@@ -3568,31 +3583,39 @@ impl BackgroundScanner {
         // If the worktree root does not contain a git repository, then find
         // the git repository in an ancestor directory. Find any gitignore files
         // in ancestor directories.
-        let root_abs_path = self.state.lock().snapshot.abs_path.clone();
+        let root_abs_path = self.state.lock().await.snapshot.abs_path.clone();
         let (ignores, repo) = discover_ancestor_git_repo(self.fs.clone(), &root_abs_path).await;
         self.state
             .lock()
+            .await
             .snapshot
             .ignores_by_parent_abs_path
             .extend(ignores);
-        let containing_git_repository = repo.and_then(|(ancestor_dot_git, work_directory)| {
-            self.state
-                .lock()
-                .insert_git_repository_for_path(
-                    work_directory,
-                    ancestor_dot_git.clone().into(),
-                    self.fs.as_ref(),
-                    self.watcher.as_ref(),
-                )
-                .log_err()?;
-            Some(ancestor_dot_git)
-        });
+        let containing_git_repository = if let Some((ancestor_dot_git, work_directory)) = repo {
+            maybe!(async {
+                self.state
+                    .lock()
+                    .await
+                    .insert_git_repository_for_path(
+                        work_directory,
+                        ancestor_dot_git.clone().into(),
+                        self.fs.as_ref(),
+                        self.watcher.as_ref(),
+                    )
+                    .await
+                    .log_err()?;
+                Some(ancestor_dot_git)
+            })
+            .await
+        } else {
+            None
+        };
 
         log::trace!("containing git repository: {containing_git_repository:?}");
 
         let mut global_gitignore_events =
             if let Some(global_gitignore_path) = &paths::global_gitignore_path() {
-                self.state.lock().snapshot.global_gitignore =
+                self.state.lock().await.snapshot.global_gitignore =
                     if self.fs.is_file(&global_gitignore_path).await {
                         build_gitignore(global_gitignore_path, self.fs.as_ref())
                             .await
@@ -3606,31 +3629,34 @@ impl BackgroundScanner {
                     .await
                     .0
             } else {
-                self.state.lock().snapshot.global_gitignore = None;
+                self.state.lock().await.snapshot.global_gitignore = None;
                 Box::pin(futures::stream::empty())
             };
 
         let (scan_job_tx, scan_job_rx) = channel::unbounded();
         {
-            let mut state = self.state.lock();
+            let mut state = self.state.lock().await;
             state.snapshot.scan_id += 1;
             if let Some(mut root_entry) = state.snapshot.root_entry().cloned() {
-                let ignore_stack = state.snapshot.ignore_stack_for_abs_path(
-                    root_abs_path.as_path(),
-                    true,
-                    self.fs.as_ref(),
-                );
+                let ignore_stack = state
+                    .snapshot
+                    .ignore_stack_for_abs_path(root_abs_path.as_path(), true, self.fs.as_ref())
+                    .await;
                 if ignore_stack.is_abs_path_ignored(root_abs_path.as_path(), true) {
                     root_entry.is_ignored = true;
-                    state.insert_entry(root_entry.clone(), self.fs.as_ref(), self.watcher.as_ref());
+                    state
+                        .insert_entry(root_entry.clone(), self.fs.as_ref(), self.watcher.as_ref())
+                        .await;
                 }
                 if root_entry.is_dir() {
-                    state.enqueue_scan_dir(
-                        root_abs_path.as_path().into(),
-                        &root_entry,
-                        &scan_job_tx,
-                        self.fs.as_ref(),
-                    );
+                    state
+                        .enqueue_scan_dir(
+                            root_abs_path.as_path().into(),
+                            &root_entry,
+                            &scan_job_tx,
+                            self.fs.as_ref(),
+                        )
+                        .await;
                 }
             }
         };
@@ -3639,11 +3665,11 @@ impl BackgroundScanner {
         drop(scan_job_tx);
         self.scan_dirs(true, scan_job_rx).await;
         {
-            let mut state = self.state.lock();
+            let mut state = self.state.lock().await;
             state.snapshot.completed_scan_id = state.snapshot.scan_id;
         }
 
-        self.send_status_update(false, SmallVec::new());
+        self.send_status_update(false, SmallVec::new()).await;
 
         // Process any any FS events that occurred while performing the initial scan.
         // For these events, update events cannot be as precise, because we didn't
@@ -3688,7 +3714,7 @@ impl BackgroundScanner {
                     if did_scan {
                         let abs_path =
                         {
-                            let mut state = self.state.lock();
+                            let mut state = self.state.lock().await;
                             state.path_prefixes_to_scan.insert(request.path.clone());
                             state.snapshot.absolutize(&request.path)
                         };
@@ -3697,7 +3723,7 @@ impl BackgroundScanner {
                             self.process_events(vec![abs_path]).await;
                         }
                     }
-                    self.send_status_update(false, request.done);
+                    self.send_status_update(false, request.done).await;
                 }
 
                 paths = fs_events_rx.next().fuse() => {
@@ -3726,7 +3752,7 @@ impl BackgroundScanner {
         request.relative_paths.sort_unstable();
         self.forcibly_load_paths(&request.relative_paths).await;
 
-        let root_path = self.state.lock().snapshot.abs_path.clone();
+        let root_path = self.state.lock().await.snapshot.abs_path.clone();
         let root_canonical_path = self.fs.canonicalize(root_path.as_path()).await;
         let root_canonical_path = match &root_canonical_path {
             Ok(path) => SanitizedPath::new(path),
@@ -3748,7 +3774,7 @@ impl BackgroundScanner {
             .collect::<Vec<_>>();
 
         {
-            let mut state = self.state.lock();
+            let mut state = self.state.lock().await;
             let is_idle = state.snapshot.completed_scan_id == state.snapshot.scan_id;
             state.snapshot.scan_id += 1;
             if is_idle {
@@ -3765,11 +3791,11 @@ impl BackgroundScanner {
         )
         .await;
 
-        self.send_status_update(scanning, request.done)
+        self.send_status_update(scanning, request.done).await
     }
 
     async fn process_events(&self, mut abs_paths: Vec<PathBuf>) {
-        let root_path = self.state.lock().snapshot.abs_path.clone();
+        let root_path = self.state.lock().await.snapshot.abs_path.clone();
         let root_canonical_path = self.fs.canonicalize(root_path.as_path()).await;
         let root_canonical_path = match &root_canonical_path {
             Ok(path) => SanitizedPath::new(path),
@@ -3777,6 +3803,7 @@ impl BackgroundScanner {
                 let new_path = self
                     .state
                     .lock()
+                    .await
                     .snapshot
                     .root_file_handle
                     .clone()
@@ -3809,24 +3836,31 @@ impl BackgroundScanner {
         let mut dot_git_abs_paths = Vec::new();
         abs_paths.sort_unstable();
         abs_paths.dedup_by(|a, b| a.starts_with(b));
-        abs_paths.retain(|abs_path| {
+        {
+            let snapshot = &self.state.lock().await.snapshot;
+            abs_paths.retain(|abs_path| {
             let abs_path = &SanitizedPath::new(abs_path);
 
-            let snapshot = &self.state.lock().snapshot;
+
             {
                 let mut is_git_related = false;
 
-                let dot_git_paths = abs_path.as_path().ancestors().find_map(|ancestor| {
-                    if smol::block_on(is_git_dir(ancestor, self.fs.as_ref())) {
+                let dot_git_paths = self.executor.block(maybe!(async  {
+                    let mut path = None;
+                    for ancestor in abs_path.as_path().ancestors() {
+
+                    if is_git_dir(ancestor, self.fs.as_ref()).await {
                         let path_in_git_dir = abs_path
                             .as_path()
                             .strip_prefix(ancestor)
                             .expect("stripping off the ancestor");
-                        Some((ancestor.to_owned(), path_in_git_dir.to_owned()))
-                    } else {
-                        None
+                       path = Some((ancestor.to_owned(), path_in_git_dir.to_owned()));
+                       break;
                     }
-                });
+                    }
+                    path
+
+                }));
 
                 if let Some((dot_git_abs_path, path_in_git_dir)) = dot_git_paths {
                     if skipped_files_in_dot_git
@@ -3899,12 +3933,12 @@ impl BackgroundScanner {
                 true
             }
         });
-
+        }
         if relative_paths.is_empty() && dot_git_abs_paths.is_empty() {
             return;
         }
 
-        self.state.lock().snapshot.scan_id += 1;
+        self.state.lock().await.snapshot.scan_id += 1;
 
         let (scan_job_tx, scan_job_rx) = channel::unbounded();
         log::debug!("received fs events {:?}", relative_paths);
@@ -3918,29 +3952,29 @@ impl BackgroundScanner {
         .await;
 
         let affected_repo_roots = if !dot_git_abs_paths.is_empty() {
-            self.update_git_repositories(dot_git_abs_paths)
+            self.update_git_repositories(dot_git_abs_paths).await
         } else {
             Vec::new()
         };
 
         {
-            let mut ignores_to_update = self.ignores_needing_update();
+            let mut ignores_to_update = self.ignores_needing_update().await;
             ignores_to_update.extend(affected_repo_roots);
-            let ignores_to_update = self.order_ignores(ignores_to_update);
-            let snapshot = self.state.lock().snapshot.clone();
+            let ignores_to_update = self.order_ignores(ignores_to_update).await;
+            let snapshot = self.state.lock().await.snapshot.clone();
             self.update_ignore_statuses_for_paths(scan_job_tx, snapshot, ignores_to_update)
                 .await;
             self.scan_dirs(false, scan_job_rx).await;
         }
 
         {
-            let mut state = self.state.lock();
+            let mut state = self.state.lock().await;
             state.snapshot.completed_scan_id = state.snapshot.scan_id;
             for (_, entry) in mem::take(&mut state.removed_entries) {
                 state.scanned_dirs.remove(&entry.id);
             }
         }
-        self.send_status_update(false, SmallVec::new());
+        self.send_status_update(false, SmallVec::new()).await;
     }
 
     async fn update_global_gitignore(&self, abs_path: &Path) {
@@ -3949,30 +3983,30 @@ impl BackgroundScanner {
             .log_err()
             .map(Arc::new);
         let (prev_snapshot, ignore_stack, abs_path) = {
-            let mut state = self.state.lock();
+            let mut state = self.state.lock().await;
             state.snapshot.global_gitignore = ignore;
             let abs_path = state.snapshot.abs_path().clone();
-            let ignore_stack =
-                state
-                    .snapshot
-                    .ignore_stack_for_abs_path(&abs_path, true, self.fs.as_ref());
+            let ignore_stack = state
+                .snapshot
+                .ignore_stack_for_abs_path(&abs_path, true, self.fs.as_ref())
+                .await;
             (state.snapshot.clone(), ignore_stack, abs_path)
         };
         let (scan_job_tx, scan_job_rx) = channel::unbounded();
         self.update_ignore_statuses_for_paths(
             scan_job_tx,
             prev_snapshot,
-            vec![(abs_path, ignore_stack)].into_iter(),
+            vec![(abs_path, ignore_stack)],
         )
         .await;
         self.scan_dirs(false, scan_job_rx).await;
-        self.send_status_update(false, SmallVec::new());
+        self.send_status_update(false, SmallVec::new()).await;
     }
 
     async fn forcibly_load_paths(&self, paths: &[Arc<RelPath>]) -> bool {
         let (scan_job_tx, scan_job_rx) = channel::unbounded();
         {
-            let mut state = self.state.lock();
+            let mut state = self.state.lock().await;
             let root_path = state.snapshot.abs_path.clone();
             for path in paths {
                 for ancestor in path.ancestors() {
@@ -3980,12 +4014,14 @@ impl BackgroundScanner {
                         && entry.kind == EntryKind::UnloadedDir
                     {
                         let abs_path = root_path.join(ancestor.as_std_path());
-                        state.enqueue_scan_dir(
-                            abs_path.into(),
-                            entry,
-                            &scan_job_tx,
-                            self.fs.as_ref(),
-                        );
+                        state
+                            .enqueue_scan_dir(
+                                abs_path.into(),
+                                entry,
+                                &scan_job_tx,
+                                self.fs.as_ref(),
+                            )
+                            .await;
                         state.paths_to_scan.insert(path.clone());
                         break;
                     }
@@ -3997,7 +4033,7 @@ impl BackgroundScanner {
             self.scan_dir(&job).await.log_err();
         }
 
-        !mem::take(&mut self.state.lock().paths_to_scan).is_empty()
+        !mem::take(&mut self.state.lock().await.paths_to_scan).is_empty()
     }
 
     async fn scan_dirs(
@@ -4045,7 +4081,7 @@ impl BackgroundScanner {
                                     ) {
                                         Ok(_) => {
                                             last_progress_update_count += 1;
-                                            self.send_status_update(true, SmallVec::new());
+                                            self.send_status_update(true, SmallVec::new()).await;
                                         }
                                         Err(count) => {
                                             last_progress_update_count = count;
@@ -4070,8 +4106,12 @@ impl BackgroundScanner {
             .await;
     }
 
-    fn send_status_update(&self, scanning: bool, barrier: SmallVec<[barrier::Sender; 1]>) -> bool {
-        let mut state = self.state.lock();
+    async fn send_status_update(
+        &self,
+        scanning: bool,
+        barrier: SmallVec<[barrier::Sender; 1]>,
+    ) -> bool {
+        let mut state = self.state.lock().await;
         if state.changed_paths.is_empty() && scanning {
             return true;
         }
@@ -4100,7 +4140,7 @@ impl BackgroundScanner {
         let root_abs_path;
         let root_char_bag;
         {
-            let snapshot = &self.state.lock().snapshot;
+            let snapshot = &self.state.lock().await.snapshot;
             if self.settings.is_path_excluded(&job.path) {
                 log::error!("skipping excluded directory {:?}", job.path);
                 return Ok(());
@@ -4153,12 +4193,14 @@ impl BackgroundScanner {
             };
 
             if child_name == DOT_GIT {
-                let mut state = self.state.lock();
-                state.insert_git_repository(
-                    child_path.clone(),
-                    self.fs.as_ref(),
-                    self.watcher.as_ref(),
-                );
+                let mut state = self.state.lock().await;
+                state
+                    .insert_git_repository(
+                        child_path.clone(),
+                        self.fs.as_ref(),
+                        self.watcher.as_ref(),
+                    )
+                    .await;
             } else if child_name == GITIGNORE {
                 match build_gitignore(&child_abs_path, self.fs.as_ref()).await {
                     Ok(ignore) => {
@@ -4178,7 +4220,7 @@ impl BackgroundScanner {
 
             if self.settings.is_path_excluded(&child_path) {
                 log::debug!("skipping excluded child entry {child_path:?}");
-                self.state.lock().remove_path(&child_path);
+                self.state.lock().await.remove_path(&child_path);
                 continue;
             }
 
@@ -4278,7 +4320,7 @@ impl BackgroundScanner {
             new_entries.push(child_entry);
         }
 
-        let mut state = self.state.lock();
+        let mut state = self.state.lock().await;
 
         // Identify any subdirectories that should not be scanned.
         let mut job_ix = 0;
@@ -4360,7 +4402,7 @@ impl BackgroundScanner {
             None
         };
 
-        let mut state = self.state.lock();
+        let mut state = self.state.lock().await;
         let doing_recursive_update = scan_queue_tx.is_some();
 
         // Remove any entries for paths that no longer exist or are being recursively
@@ -4377,11 +4419,10 @@ impl BackgroundScanner {
             let abs_path: Arc<Path> = root_abs_path.join(path.as_std_path()).into();
             match metadata {
                 Ok(Some((metadata, canonical_path))) => {
-                    let ignore_stack = state.snapshot.ignore_stack_for_abs_path(
-                        &abs_path,
-                        metadata.is_dir,
-                        self.fs.as_ref(),
-                    );
+                    let ignore_stack = state
+                        .snapshot
+                        .ignore_stack_for_abs_path(&abs_path, metadata.is_dir, self.fs.as_ref())
+                        .await;
                     let is_external = !canonical_path.starts_with(&root_canonical_path);
                     let mut fs_entry = Entry::new(
                         path.clone(),
@@ -4413,18 +4454,22 @@ impl BackgroundScanner {
                             || (fs_entry.path.is_empty()
                                 && abs_path.file_name() == Some(OsStr::new(DOT_GIT)))
                         {
-                            state.enqueue_scan_dir(
-                                abs_path,
-                                &fs_entry,
-                                scan_queue_tx,
-                                self.fs.as_ref(),
-                            );
+                            state
+                                .enqueue_scan_dir(
+                                    abs_path,
+                                    &fs_entry,
+                                    scan_queue_tx,
+                                    self.fs.as_ref(),
+                                )
+                                .await;
                         } else {
                             fs_entry.kind = EntryKind::UnloadedDir;
                         }
                     }
 
-                    state.insert_entry(fs_entry.clone(), self.fs.as_ref(), self.watcher.as_ref());
+                    state
+                        .insert_entry(fs_entry.clone(), self.fs.as_ref(), self.watcher.as_ref())
+                        .await;
 
                     if path.is_empty()
                         && let Some((ignores, repo)) = new_ancestor_repo.take()
@@ -4439,6 +4484,7 @@ impl BackgroundScanner {
                                     self.fs.as_ref(),
                                     self.watcher.as_ref(),
                                 )
+                                .await
                                 .log_err();
                         }
                     }
@@ -4477,11 +4523,11 @@ impl BackgroundScanner {
         &self,
         scan_job_tx: Sender<ScanJob>,
         prev_snapshot: LocalSnapshot,
-        mut ignores_to_update: impl Iterator<Item = (Arc<Path>, IgnoreStack)>,
+        ignores_to_update: Vec<(Arc<Path>, IgnoreStack)>,
     ) {
         let (ignore_queue_tx, ignore_queue_rx) = channel::unbounded();
         {
-            while let Some((parent_abs_path, ignore_stack)) = ignores_to_update.next() {
+            for (parent_abs_path, ignore_stack) in ignores_to_update {
                 ignore_queue_tx
                     .send_blocking(UpdateIgnoreStatusJob {
                         abs_path: parent_abs_path,
@@ -4522,11 +4568,11 @@ impl BackgroundScanner {
             .await;
     }
 
-    fn ignores_needing_update(&self) -> Vec<Arc<Path>> {
+    async fn ignores_needing_update(&self) -> Vec<Arc<Path>> {
         let mut ignores_to_update = Vec::new();
 
         {
-            let snapshot = &mut self.state.lock().snapshot;
+            let snapshot = &mut self.state.lock().await.snapshot;
             let abs_path = snapshot.abs_path.clone();
             snapshot
                 .ignores_by_parent_abs_path
@@ -4554,26 +4600,27 @@ impl BackgroundScanner {
         ignores_to_update
     }
 
-    fn order_ignores(
-        &self,
-        mut ignores: Vec<Arc<Path>>,
-    ) -> impl use<> + Iterator<Item = (Arc<Path>, IgnoreStack)> {
+    async fn order_ignores(&self, mut ignores: Vec<Arc<Path>>) -> Vec<(Arc<Path>, IgnoreStack)> {
         let fs = self.fs.clone();
-        let snapshot = self.state.lock().snapshot.clone();
+        let snapshot = self.state.lock().await.snapshot.clone();
         ignores.sort_unstable();
         let mut ignores_to_update = ignores.into_iter().peekable();
-        std::iter::from_fn(move || {
-            let parent_abs_path = ignores_to_update.next()?;
+
+        let mut result = vec![];
+        while let Some(parent_abs_path) = ignores_to_update.next() {
             while ignores_to_update
                 .peek()
                 .map_or(false, |p| p.starts_with(&parent_abs_path))
             {
                 ignores_to_update.next().unwrap();
             }
-            let ignore_stack =
-                snapshot.ignore_stack_for_abs_path(&parent_abs_path, true, fs.as_ref());
-            Some((parent_abs_path, ignore_stack))
-        })
+            let ignore_stack = snapshot
+                .ignore_stack_for_abs_path(&parent_abs_path, true, fs.as_ref())
+                .await;
+            result.push((parent_abs_path, ignore_stack));
+        }
+
+        result
     }
 
     async fn update_ignore_status(&self, job: UpdateIgnoreStatusJob, snapshot: &LocalSnapshot) {
@@ -4605,7 +4652,7 @@ impl BackgroundScanner {
             return;
         };
 
-        if let Ok(Some(metadata)) = smol::block_on(self.fs.metadata(&job.abs_path.join(DOT_GIT)))
+        if let Ok(Some(metadata)) = self.fs.metadata(&job.abs_path.join(DOT_GIT)).await
             && metadata.is_dir
         {
             ignore_stack.repo_root = Some(job.abs_path.clone());
@@ -4625,14 +4672,16 @@ impl BackgroundScanner {
 
                 // Scan any directories that were previously ignored and weren't previously scanned.
                 if was_ignored && !entry.is_ignored && entry.kind.is_unloaded() {
-                    let state = self.state.lock();
+                    let state = self.state.lock().await;
                     if state.should_scan_directory(&entry) {
-                        state.enqueue_scan_dir(
-                            abs_path.clone(),
-                            &entry,
-                            &job.scan_queue,
-                            self.fs.as_ref(),
-                        );
+                        state
+                            .enqueue_scan_dir(
+                                abs_path.clone(),
+                                &entry,
+                                &job.scan_queue,
+                                self.fs.as_ref(),
+                            )
+                            .await;
                     }
                 }
 
@@ -4656,7 +4705,7 @@ impl BackgroundScanner {
             }
         }
 
-        let state = &mut self.state.lock();
+        let state = &mut self.state.lock().await;
         for edit in &entries_by_path_edits {
             if let Edit::Insert(entry) = edit
                 && let Err(ix) = state.changed_paths.binary_search(&entry.path)
@@ -4672,9 +4721,9 @@ impl BackgroundScanner {
         state.snapshot.entries_by_id.edit(entries_by_id_edits, ());
     }
 
-    fn update_git_repositories(&self, dot_git_paths: Vec<PathBuf>) -> Vec<Arc<Path>> {
+    async fn update_git_repositories(&self, dot_git_paths: Vec<PathBuf>) -> Vec<Arc<Path>> {
         log::trace!("reloading repositories: {dot_git_paths:?}");
-        let mut state = self.state.lock();
+        let mut state = self.state.lock().await;
         let scan_id = state.snapshot.scan_id;
         let mut affected_repo_roots = Vec::new();
         for dot_git_dir in dot_git_paths {
@@ -4704,13 +4753,15 @@ impl BackgroundScanner {
                         return Vec::new();
                     };
                     affected_repo_roots.push(dot_git_dir.parent().unwrap().into());
-                    state.insert_git_repository(
-                        RelPath::new(relative, PathStyle::local())
-                            .unwrap()
-                            .into_arc(),
-                        self.fs.as_ref(),
-                        self.watcher.as_ref(),
-                    );
+                    state
+                        .insert_git_repository(
+                            RelPath::new(relative, PathStyle::local())
+                                .unwrap()
+                                .into_arc(),
+                            self.fs.as_ref(),
+                            self.watcher.as_ref(),
+                        )
+                        .await;
                 }
                 Some(local_repository) => {
                     state.snapshot.git_repositories.update(
@@ -4738,7 +4789,7 @@ impl BackgroundScanner {
 
             if exists_in_snapshot
                 || matches!(
-                    smol::block_on(self.fs.metadata(&entry.common_dir_abs_path)),
+                    self.fs.metadata(&entry.common_dir_abs_path).await,
                     Ok(Some(_))
                 )
             {
@@ -5497,11 +5548,13 @@ fn parse_gitfile(content: &str) -> anyhow::Result<&Path> {
     Ok(Path::new(path.trim()))
 }
 
-fn discover_git_paths(dot_git_abs_path: &Arc<Path>, fs: &dyn Fs) -> (Arc<Path>, Arc<Path>) {
+async fn discover_git_paths(dot_git_abs_path: &Arc<Path>, fs: &dyn Fs) -> (Arc<Path>, Arc<Path>) {
     let mut repository_dir_abs_path = dot_git_abs_path.clone();
     let mut common_dir_abs_path = dot_git_abs_path.clone();
 
-    if let Some(path) = smol::block_on(fs.load(dot_git_abs_path))
+    if let Some(path) = fs
+        .load(dot_git_abs_path)
+        .await
         .ok()
         .as_ref()
         .and_then(|contents| parse_gitfile(contents).log_err())
@@ -5510,17 +5563,19 @@ fn discover_git_paths(dot_git_abs_path: &Arc<Path>, fs: &dyn Fs) -> (Arc<Path>,
             .parent()
             .unwrap_or(Path::new(""))
             .join(path);
-        if let Some(path) = smol::block_on(fs.canonicalize(&path)).log_err() {
+        if let Some(path) = fs.canonicalize(&path).await.log_err() {
             repository_dir_abs_path = Path::new(&path).into();
             common_dir_abs_path = repository_dir_abs_path.clone();
-            if let Some(commondir_contents) = smol::block_on(fs.load(&path.join("commondir"))).ok()
-                && let Some(commondir_path) =
-                    smol::block_on(fs.canonicalize(&path.join(commondir_contents.trim()))).log_err()
+
+            if let Some(commondir_contents) = fs.load(&path.join("commondir")).await.ok()
+                && let Some(commondir_path) = fs
+                    .canonicalize(&path.join(commondir_contents.trim()))
+                    .await
+                    .log_err()
             {
                 common_dir_abs_path = commondir_path.as_path().into();
             }
         }
     };
-
     (repository_dir_abs_path, common_dir_abs_path)
 }