nvme/tcp: check PDU type before checking padding

Not all PDUs that have can have data can also have padding - e.g.
C2HTermReq has data, but cannot have padding and the PDO field should be
reserved.  Therefore, for these PDUs the data starts exactly at the end
of the header (and its digest, if present) and we shouldn't be using PDO
to calculate its offset.

This fixes handling for the C2HTermReq PDUs, as it used to be broken and
usually (if target set PDO=0) resulted in an overflow when calculating
psh_len.

Signed-off-by: Konrad Sztyber <konrad.sztyber@intel.com>
Change-Id: Ia2976517019469ba375eb32d22739372211eff35
Reviewed-on: https://review.spdk.io/gerrit/c/spdk/spdk/+/12846
Community-CI: Broadcom CI <spdk-ci.pdl@broadcom.com>
Community-CI: Mellanox Build Bot
Tested-by: SPDK CI Jenkins <sys_sgci@intel.com>
Reviewed-by: Jim Harris <james.r.harris@intel.com>
Reviewed-by: Aleksey Marchuk <alexeymar@nvidia.com>
This commit is contained in:
Konrad Sztyber 2022-05-31 16:56:37 +02:00 committed by Tomasz Zawadzki
parent 1f3bd08fa0
commit 5088a8930d

View File

@ -558,10 +558,19 @@ nvme_tcp_pdu_calc_psh_len(struct nvme_tcp_pdu *pdu, bool hdgst_enable)
psh_len += SPDK_NVME_TCP_DIGEST_LEN; psh_len += SPDK_NVME_TCP_DIGEST_LEN;
} }
if (pdu->hdr.common.plen > psh_len) { if (pdu->hdr.common.plen > psh_len) {
pdo = pdu->hdr.common.pdo; switch (pdu->hdr.common.pdu_type) {
padding_len = pdo - psh_len; case SPDK_NVME_TCP_PDU_TYPE_CAPSULE_CMD:
if (padding_len > 0) { case SPDK_NVME_TCP_PDU_TYPE_H2C_DATA:
psh_len = pdo; case SPDK_NVME_TCP_PDU_TYPE_C2H_DATA:
pdo = pdu->hdr.common.pdo;
padding_len = pdo - psh_len;
if (padding_len > 0) {
psh_len = pdo;
}
break;
default:
/* There is no padding for other PDU types */
break;
} }
} }