git: d1516ec33e66 - main - nvmf: Fail pass through commands while a controller is not associated

From: John Baldwin <jhb_at_FreeBSD.org>
Date: Thu, 17 Oct 2024 16:10:11 UTC
The branch main has been updated by jhb:

URL: https://cgit.FreeBSD.org/src/commit/?id=d1516ec33e6600f6aae3243119aeb14762dc9f97

commit d1516ec33e6600f6aae3243119aeb14762dc9f97
Author:     John Baldwin <jhb@FreeBSD.org>
AuthorDate: 2024-10-17 16:09:27 +0000
Commit:     John Baldwin <jhb@FreeBSD.org>
CommitDate: 2024-10-17 16:09:27 +0000

    nvmf: Fail pass through commands while a controller is not associated
    
    Previously this just dereferenced NULL qp pointers and panicked.
    Instead, use a shared lock on the connection lock to protect access to
    the qp pointers and allocate a request.  If the controller is not
    associated, fail the request with ECONNABORTED.
    
    Possibly this should be honoring kern.nvmf.fail_on_disconnection and
    block waiting for a reconnect request while disconnected if that
    tunable is false.
    
    Reported by:    Suhas Lokesha <suhas@chelsio.com>
    Sponsored by:   Chelsio Communications
---
 sys/dev/nvmf/host/nvmf.c | 9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/sys/dev/nvmf/host/nvmf.c b/sys/dev/nvmf/host/nvmf.c
index 623c76954720..12023ebf96f9 100644
--- a/sys/dev/nvmf/host/nvmf.c
+++ b/sys/dev/nvmf/host/nvmf.c
@@ -972,12 +972,21 @@ nvmf_passthrough_cmd(struct nvmf_softc *sc, struct nvme_pt_command *pt,
 	cmd.cdw14 = pt->cmd.cdw14;
 	cmd.cdw15 = pt->cmd.cdw15;
 
+	sx_slock(&sc->connection_lock);
+	if (sc->admin == NULL || sc->detaching) {
+		device_printf(sc->dev,
+		    "failed to send passthrough command\n");
+		error = ECONNABORTED;
+		sx_sunlock(&sc->connection_lock);
+		goto error;
+	}
 	if (admin)
 		qp = sc->admin;
 	else
 		qp = nvmf_select_io_queue(sc);
 	nvmf_status_init(&status);
 	req = nvmf_allocate_request(qp, &cmd, nvmf_complete, &status, M_WAITOK);
+	sx_sunlock(&sc->connection_lock);
 	if (req == NULL) {
 		device_printf(sc->dev, "failed to send passthrough command\n");
 		error = ECONNABORTED;