Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Misc nvme/block fixes #657

Merged
merged 3 commits into from
Mar 7, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions lib/propolis/src/block/backend.rs
Original file line number Diff line number Diff line change
Expand Up @@ -182,6 +182,7 @@ impl Attachment {
pub fn notify(&self) {
// TODO: avoid thundering herd?
self.0.req_notifier.notify_waiters();
let _guard = self.0.state.lock().unwrap();
self.0.cv.notify_all();
}
}
Expand Down
25 changes: 14 additions & 11 deletions lib/propolis/src/hw/nvme/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -618,7 +618,7 @@ impl PciNvme {

let cur = state.ctrl.cc;
if new.enabled() && !cur.enabled() {
slog::info!(self.log, "Enabling controller");
slog::debug!(self.log, "Enabling controller");

let mem = self.mem_access();
let mem = mem.ok_or(NvmeError::MemoryInaccessible)?;
Expand All @@ -635,7 +635,7 @@ impl PciNvme {
state.ctrl.csts.set_ready(true);
}
} else if !new.enabled() && cur.enabled() {
slog::info!(self.log, "Disabling controller");
slog::debug!(self.log, "Disabling controller");

// Reset controller state which will set CC.EN=0 and CSTS.RDY=0
state.reset();
Expand Down Expand Up @@ -840,20 +840,23 @@ impl PciNvme {
// Completion Queue y Head Doorbell
let cq = state.get_cq(qid)?;
cq.notify_head(val)?;

// We may have skipped pulling entries off some SQ due to this
// CQ having no available entry slots. Since we've just freed
// up some slots, notify any attached block backend that
// there may be new requests available.
self.block_attach.notify();
} else {
// Submission Queue y Tail Doorbell
let sq = state.get_sq(qid)?;
sq.notify_tail(val)?;

// Poke block backend to service new requests
self.block_attach.notify();
}

// Poke block backend to service new requests
//
// This is done for CQs in addition to SQs, since we may have
// skipped pulling entries off some SQ due to CQs having no
// available entry slots.
//
// The state lock must be released before issuing the
// notification to avoid deadlocking with the block backend
// attempting to fetch new requests.
drop(state);
self.block_attach.notify();
}
}

Expand Down
Loading