diff --git a/lib/nvme/nvme_ctrlr.c b/lib/nvme/nvme_ctrlr.c index 3ac131b4c..37f8a83ab 100644 --- a/lib/nvme/nvme_ctrlr.c +++ b/lib/nvme/nvme_ctrlr.c @@ -4198,13 +4198,15 @@ nvme_cmd_map_prps(void *prv, struct spdk_nvme_cmd *cmd, struct iovec *iovs, SPDK_ERRLOG("GPA to VVA failed\n"); return -EINVAL; } + len -= residue_len; + if (len && max_iovcnt < 2) { + SPDK_ERRLOG("Too many page entries, at least two iovs are required\n"); + return -ERANGE; + } iovs[0].iov_base = vva; iovs[0].iov_len = residue_len; - len -= residue_len; if (len) { - assert(max_iovcnt > 1); - if (spdk_unlikely(prp2 == 0)) { SPDK_ERRLOG("no PRP2, %d remaining\n", len); return -EINVAL; diff --git a/test/unit/lib/nvme/nvme_ctrlr.c/nvme_ctrlr_ut.c b/test/unit/lib/nvme/nvme_ctrlr.c/nvme_ctrlr_ut.c index 0c29a4b64..6ef4d5454 100644 --- a/test/unit/lib/nvme/nvme_ctrlr.c/nvme_ctrlr_ut.c +++ b/test/unit/lib/nvme/nvme_ctrlr.c/nvme_ctrlr_ut.c @@ -2262,6 +2262,8 @@ test_nvme_cmd_map_prps(void) cmd.dptr.prp.prp1 = (uint64_t)(uintptr_t)buf + 1024 * 3; cmd.dptr.prp.prp2 = (uint64_t)(uintptr_t)buf + 4096; len = 4096; + ret = nvme_cmd_map_prps(NULL, &cmd, iovs, 1, len, mps, gpa_to_vva); + CU_ASSERT(ret == -ERANGE); ret = nvme_cmd_map_prps(NULL, &cmd, iovs, 33, len, mps, gpa_to_vva); CU_ASSERT(ret == 2); CU_ASSERT(iovs[0].iov_base == (void *)(uintptr_t)cmd.dptr.prp.prp1);