From 2e4ff9a26efa6aa19f5258d22d41dbee58f4fa17 Mon Sep 17 00:00:00 2001 From: Niko Matsakis Date: Tue, 30 Oct 2018 16:30:12 -0400 Subject: [PATCH] remove use of upgradable reads from derived queries --- src/debug.rs | 1 - src/derived.rs | 33 +++++++++++++++------------------ 2 files changed, 15 insertions(+), 19 deletions(-) diff --git a/src/debug.rs b/src/debug.rs index f53868a..00cb2f2 100644 --- a/src/debug.rs +++ b/src/debug.rs @@ -3,7 +3,6 @@ use crate::plumbing; use crate::plumbing::QueryStorageOps; -use crate::Database; use crate::Query; use crate::QueryTable; use std::iter::FromIterator; diff --git a/src/derived.rs b/src/derived.rs index f7b9fe4..0475b5e 100644 --- a/src/derived.rs +++ b/src/derived.rs @@ -13,7 +13,7 @@ use crate::runtime::StampedValue; use crate::{Database, Event, EventKind, SweepStrategy}; use log::{debug, info}; use parking_lot::Mutex; -use parking_lot::{RwLock, RwLockUpgradableReadGuard}; +use parking_lot::RwLock; use rustc_hash::FxHashMap; use smallvec::SmallVec; use std::marker::PhantomData; @@ -284,24 +284,21 @@ where // Check with an upgradable read to see if there is a value // already. (This permits other readers but prevents anyone // else from running `read_upgrade` at the same time.) - let mut old_memo = match self.probe( - db, - self.map.upgradable_read(), - runtime, - revision_now, - descriptor, - key, - ) { - ProbeState::UpToDate(v) => return v, - ProbeState::StaleOrAbsent(map) => { - let mut map = RwLockUpgradableReadGuard::upgrade(map); - match map.insert(key.clone(), QueryState::in_progress(runtime.id())) { - Some(QueryState::Memoized(old_memo)) => Some(old_memo), - Some(QueryState::InProgress { .. }) => unreachable!(), - None => None, + // + // FIXME(Amanieu/parking_lot#101) -- we are using a write-lock + // and not an upgradable read here because upgradable reads + // can sometimes encounter deadlocks. + let mut old_memo = + match self.probe(db, self.map.write(), runtime, revision_now, descriptor, key) { + ProbeState::UpToDate(v) => return v, + ProbeState::StaleOrAbsent(mut map) => { + match map.insert(key.clone(), QueryState::in_progress(runtime.id())) { + Some(QueryState::Memoized(old_memo)) => Some(old_memo), + Some(QueryState::InProgress { .. }) => unreachable!(), + None => None, + } } - } - }; + }; let panic_guard = PanicGuard::new(&self.map, key, descriptor, runtime);