From b17d16fb47b49919725436b731405ab32a0c02f2 Mon Sep 17 00:00:00 2001 From: Arek Kusztal Date: Mon, 28 Jun 2021 17:34:29 +0100 Subject: [PATCH] common/qat: add PF to VF communication Add communication between physical device and virtual function in Intel QucikAssist Technology PMD. Signed-off-by: Arek Kusztal Acked-by: Fan Zhang Acked-by: Akhil Goyal --- drivers/common/qat/meson.build | 1 + drivers/common/qat/qat_adf/adf_pf2vf_msg.h | 154 +++++++++++++++++++++ drivers/common/qat/qat_device.c | 22 ++- drivers/common/qat/qat_device.h | 12 ++ drivers/common/qat/qat_pf2vf.c | 80 +++++++++++ drivers/common/qat/qat_pf2vf.h | 19 +++ 6 files changed, 287 insertions(+), 1 deletion(-) create mode 100644 drivers/common/qat/qat_adf/adf_pf2vf_msg.h create mode 100644 drivers/common/qat/qat_pf2vf.c create mode 100644 drivers/common/qat/qat_pf2vf.h diff --git a/drivers/common/qat/meson.build b/drivers/common/qat/meson.build index 479a46f9f0..053c219fed 100644 --- a/drivers/common/qat/meson.build +++ b/drivers/common/qat/meson.build @@ -49,6 +49,7 @@ sources += files( 'qat_qp.c', 'qat_device.c', 'qat_logs.c', + 'qat_pf2vf.c', ) includes += include_directories( 'qat_adf', diff --git a/drivers/common/qat/qat_adf/adf_pf2vf_msg.h b/drivers/common/qat/qat_adf/adf_pf2vf_msg.h new file mode 100644 index 0000000000..4029b1c14a --- /dev/null +++ b/drivers/common/qat/qat_adf/adf_pf2vf_msg.h @@ -0,0 +1,154 @@ +/* SPDX-License-Identifier: (BSD-3-Clause OR GPL-2.0) + * Copyright(c) 2021 Intel Corporation + */ +#ifndef ADF_PF2VF_MSG_H_ +#define ADF_PF2VF_MSG_H_ + +/* VF/PF compatibility version. */ +/* ADF_PFVF_COMPATIBILITY_EXT_CAP: Support for extended capabilities */ +#define ADF_PFVF_COMPATIBILITY_CAPABILITIES 2 +/* ADF_PFVF_COMPATIBILITY_FAST_ACK: In-use pattern cleared by receiver */ +#define ADF_PFVF_COMPATIBILITY_FAST_ACK 3 +#define ADF_PFVF_COMPATIBILITY_RING_TO_SVC_MAP 4 +#define ADF_PFVF_COMPATIBILITY_VERSION 4 /* PF<->VF compat */ + +#define ADF_PFVF_INT 1 +#define ADF_PFVF_MSGORIGIN_SYSTEM 2 +#define ADF_PFVF_1X_MSGTYPE_SHIFT 2 +#define ADF_PFVF_1X_MSGTYPE_MASK 0xF +#define ADF_PFVF_1X_MSGDATA_SHIFT 6 +#define ADF_PFVF_1X_MSGDATA_MASK 0x3FF +#define ADF_PFVF_2X_MSGTYPE_SHIFT 2 +#define ADF_PFVF_2X_MSGTYPE_MASK 0x3F +#define ADF_PFVF_2X_MSGDATA_SHIFT 8 +#define ADF_PFVF_2X_MSGDATA_MASK 0xFFFFFF + +#define ADF_PFVF_IN_USE 0x6AC2 +#define ADF_PFVF_IN_USE_MASK 0xFFFE +#define ADF_PFVF_VF_MSG_SHIFT 16 + +/* PF->VF messages */ +#define ADF_PF2VF_MSGTYPE_RESTARTING 0x01 +#define ADF_PF2VF_MSGTYPE_VERSION_RESP 0x02 +#define ADF_PF2VF_MSGTYPE_BLOCK_RESP 0x03 +#define ADF_PF2VF_MSGTYPE_FATAL_ERROR 0x04 +/* Do not use messages which start from 0x10 to 1.x as 1.x only use + * 4 bits as message types. Hence they are only applicable to 2.0 + */ +#define ADF_PF2VF_MSGTYPE_RP_RESET_RESP 0x10 + +/* PF->VF Version Response - ADF_PF2VF_MSGTYPE_VERSION_RESP */ +#define ADF_PF2VF_VERSION_RESP_VERS_MASK 0xFF +#define ADF_PF2VF_VERSION_RESP_VERS_SHIFT 0 +#define ADF_PF2VF_VERSION_RESP_RESULT_MASK 0x03 +#define ADF_PF2VF_VERSION_RESP_RESULT_SHIFT 8 +#define ADF_PF2VF_MINORVERSION_SHIFT 0 +#define ADF_PF2VF_MAJORVERSION_SHIFT 4 +#define ADF_PF2VF_VF_COMPATIBLE 1 +#define ADF_PF2VF_VF_INCOMPATIBLE 2 +#define ADF_PF2VF_VF_COMPAT_UNKNOWN 3 + +/* PF->VF Block Response Type - ADF_PF2VF_MSGTYPE_BLOCK_RESP */ +#define ADF_PF2VF_BLOCK_RESP_TYPE_DATA 0x0 +#define ADF_PF2VF_BLOCK_RESP_TYPE_CRC 0x1 +#define ADF_PF2VF_BLOCK_RESP_TYPE_ERROR 0x2 +#define ADF_PF2VF_BLOCK_RESP_TYPE_MASK 0x03 +#define ADF_PF2VF_BLOCK_RESP_TYPE_SHIFT 0 +#define ADF_PF2VF_BLOCK_RESP_DATA_MASK 0xFF +#define ADF_PF2VF_BLOCK_RESP_DATA_SHIFT 2 + +/* + * PF->VF Block Error Code - Returned in data field when the + * response type indicates an error + */ +#define ADF_PF2VF_INVALID_BLOCK_TYPE 0x0 +#define ADF_PF2VF_INVALID_BYTE_NUM_REQ 0x1 +#define ADF_PF2VF_PAYLOAD_TRUNCATED 0x2 +#define ADF_PF2VF_UNSPECIFIED_ERROR 0x3 + +/* VF->PF messages */ +#define ADF_VF2PF_MSGTYPE_INIT 0x3 +#define ADF_VF2PF_MSGTYPE_SHUTDOWN 0x4 +#define ADF_VF2PF_MSGTYPE_VERSION_REQ 0x5 +#define ADF_VF2PF_MSGTYPE_COMPAT_VER_REQ 0x6 +#define ADF_VF2PF_MSGTYPE_GET_LARGE_BLOCK_REQ 0x7 +#define ADF_VF2PF_MSGTYPE_GET_MEDIUM_BLOCK_REQ 0x8 +#define ADF_VF2PF_MSGTYPE_GET_SMALL_BLOCK_REQ 0x9 +/* Do not use messages which start from 0x10 to 1.x as 1.x only use + * 4 bits as message types. Hence they are only applicable to 2.0 + */ +#define ADF_VF2PF_MSGTYPE_RP_RESET 0x10 + +/* VF->PF Block Request Type - ADF_VF2PF_MSGTYPE_GET_xxx_BLOCK_REQ */ +#define ADF_VF2PF_MIN_SMALL_MESSAGE_TYPE 0 +#define ADF_VF2PF_MAX_SMALL_MESSAGE_TYPE \ + (ADF_VF2PF_MIN_SMALL_MESSAGE_TYPE + 15) +#define ADF_VF2PF_MIN_MEDIUM_MESSAGE_TYPE \ + (ADF_VF2PF_MAX_SMALL_MESSAGE_TYPE + 1) +#define ADF_VF2PF_MAX_MEDIUM_MESSAGE_TYPE \ + (ADF_VF2PF_MIN_MEDIUM_MESSAGE_TYPE + 7) +#define ADF_VF2PF_MIN_LARGE_MESSAGE_TYPE \ + (ADF_VF2PF_MAX_MEDIUM_MESSAGE_TYPE + 1) +#define ADF_VF2PF_MAX_LARGE_MESSAGE_TYPE \ + (ADF_VF2PF_MIN_LARGE_MESSAGE_TYPE + 3) +#define ADF_VF2PF_SMALL_PAYLOAD_SIZE 30 +#define ADF_VF2PF_MEDIUM_PAYLOAD_SIZE 62 +#define ADF_VF2PF_LARGE_PAYLOAD_SIZE 126 + +#define ADF_VF2PF_BLOCK_REQ_TYPE_SHIFT 0 +#define ADF_VF2PF_LARGE_BLOCK_REQ_TYPE_MASK 0x3 +#define ADF_VF2PF_MEDIUM_BLOCK_REQ_TYPE_MASK 0x7 +#define ADF_VF2PF_SMALL_BLOCK_REQ_TYPE_MASK 0xF + +#define ADF_VF2PF_LARGE_BLOCK_BYTE_NUM_SHIFT 2 +#define ADF_VF2PF_LARGE_BLOCK_BYTE_NUM_MASK 0x7F +#define ADF_VF2PF_MEDIUM_BLOCK_BYTE_NUM_SHIFT 3 +#define ADF_VF2PF_MEDIUM_BLOCK_BYTE_NUM_MASK 0x3F +#define ADF_VF2PF_SMALL_BLOCK_BYTE_NUM_SHIFT 4 +#define ADF_VF2PF_SMALL_BLOCK_BYTE_NUM_MASK 0x1F +#define ADF_VF2PF_BLOCK_REQ_CRC_SHIFT 9 + +/* PF-VF block message header bytes */ +#define ADF_VF2PF_BLOCK_VERSION_BYTE 0 +#define ADF_VF2PF_BLOCK_LEN_BYTE 1 +#define ADF_VF2PF_BLOCK_DATA 2 + +/* Block message types + * 0..15 - 32 byte message + * 16..23 - 64 byte message + * 24..27 - 128 byte message + * 2 - Get Capability Request message + */ +#define ADF_VF2PF_BLOCK_MSG_CAP_SUMMARY 0x2 +#define ADF_VF2PF_BLOCK_MSG_GET_RING_TO_SVC_REQ 0x3 + +/* VF->PF Compatible Version Request - ADF_VF2PF_MSGTYPE_VERSION_REQ */ +#define ADF_VF2PF_COMPAT_VER_SHIFT 0 +#define ADF_VF2PF_COMPAT_VER_MASK 0xFF + +/* How long to wait for far side to acknowledge receipt */ +#define ADF_IOV_MSG_ACK_DELAY_US 5 +#define ADF_IOV_MSG_ACK_MAX_RETRY (100 * 1000 / ADF_IOV_MSG_ACK_DELAY_US) +/* If CSR is busy, how long to delay before retrying */ +#define ADF_IOV_MSG_RETRY_DELAY 5 +#define ADF_IOV_MSG_MAX_RETRIES 3 +/* How long to wait for a response from the other side */ +#define ADF_IOV_MSG_RESP_TIMEOUT 100 +/* How often to retry when there is no response */ +#define ADF_IOV_MSG_RESP_RETRIES 5 + +#define ADF_IOV_RATELIMIT_INTERVAL 8 +#define ADF_IOV_RATELIMIT_BURST 130 +/* PF VF message byte shift */ +#define ADF_PFVF_DATA_SHIFT 8 +#define ADF_PFVF_DATA_MASK 0xFF + +/* CRC Calculation */ +#define ADF_CRC8_INIT_VALUE 0xFF + +/* Per device register offsets */ +/* GEN 4 */ +#define ADF_4XXXIOV_PF2VM_OFFSET 0x1008 +#define ADF_4XXXIOV_VM2PF_OFFSET 0x100C + +#endif /* ADF_IOV_MSG_H */ diff --git a/drivers/common/qat/qat_device.c b/drivers/common/qat/qat_device.c index 932d7110f7..5ee441171e 100644 --- a/drivers/common/qat/qat_device.c +++ b/drivers/common/qat/qat_device.c @@ -10,6 +10,17 @@ #include "adf_transport_access_macros.h" #include "qat_sym_pmd.h" #include "qat_comp_pmd.h" +#include "adf_pf2vf_msg.h" + +/* pv2vf data Gen 4*/ +struct qat_pf2vf_dev qat_pf2vf_gen4 = { + .pf2vf_offset = ADF_4XXXIOV_PF2VM_OFFSET, + .vf2pf_offset = ADF_4XXXIOV_VM2PF_OFFSET, + .pf2vf_type_shift = ADF_PFVF_2X_MSGTYPE_SHIFT, + .pf2vf_type_mask = ADF_PFVF_2X_MSGTYPE_MASK, + .pf2vf_data_shift = ADF_PFVF_2X_MSGDATA_SHIFT, + .pf2vf_data_mask = ADF_PFVF_2X_MSGDATA_MASK, +}; /* Hardware device information per generation */ __extension__ @@ -33,7 +44,8 @@ struct qat_gen_hw_data qat_gen_config[] = { [QAT_GEN4] = { .dev_gen = QAT_GEN4, .qp_hw_data = NULL, - .comp_num_im_bufs_required = QAT_NUM_INTERM_BUFS_GEN3 + .comp_num_im_bufs_required = QAT_NUM_INTERM_BUFS_GEN3, + .pf2vf_dev = &qat_pf2vf_gen4 }, }; @@ -249,6 +261,14 @@ qat_pci_device_allocate(struct rte_pci_device *pci_dev, return NULL; } + if (qat_dev->qat_dev_gen == QAT_GEN4) { + qat_dev->misc_bar_io_addr = pci_dev->mem_resource[2].addr; + if (qat_dev->misc_bar_io_addr == NULL) { + QAT_LOG(ERR, "QAT cannot get access to VF misc bar"); + return NULL; + } + } + if (devargs && devargs->drv_str) qat_dev_parse_cmd(devargs->drv_str, qat_dev_cmd_param); diff --git a/drivers/common/qat/qat_device.h b/drivers/common/qat/qat_device.h index f4fecc9517..05e164baa7 100644 --- a/drivers/common/qat/qat_device.h +++ b/drivers/common/qat/qat_device.h @@ -108,12 +108,24 @@ struct qat_pci_device { struct qat_qp_hw_data qp_gen4_data[QAT_GEN4_BUNDLE_NUM] [QAT_GEN4_QPS_PER_BUNDLE_NUM]; /**< Data of ring configuration on gen4 */ + void *misc_bar_io_addr; + /**< Address of misc bar */ }; struct qat_gen_hw_data { enum qat_device_gen dev_gen; const struct qat_qp_hw_data (*qp_hw_data)[ADF_MAX_QPS_ON_ANY_SERVICE]; enum qat_comp_num_im_buffers comp_num_im_bufs_required; + struct qat_pf2vf_dev *pf2vf_dev; +}; + +struct qat_pf2vf_dev { + uint32_t pf2vf_offset; + uint32_t vf2pf_offset; + int pf2vf_type_shift; + uint32_t pf2vf_type_mask; + int pf2vf_data_shift; + uint32_t pf2vf_data_mask; }; extern struct qat_gen_hw_data qat_gen_config[]; diff --git a/drivers/common/qat/qat_pf2vf.c b/drivers/common/qat/qat_pf2vf.c new file mode 100644 index 0000000000..6327311199 --- /dev/null +++ b/drivers/common/qat/qat_pf2vf.c @@ -0,0 +1,80 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2021 Intel Corporation + */ + +#include "qat_pf2vf.h" +#include "adf_pf2vf_msg.h" + +#include + +int qat_pf2vf_exch_msg(struct qat_pci_device *qat_dev, + struct qat_pf2vf_msg pf2vf_msg, + int len, uint8_t *ret) +{ + int i = 0; + struct qat_pf2vf_dev *qat_pf2vf = + qat_gen_config[qat_dev->qat_dev_gen].pf2vf_dev; + void *pmisc_bar_addr = qat_dev->misc_bar_io_addr; + uint32_t msg = 0, count = 0, val = 0; + uint32_t vf_csr_off = qat_pf2vf->vf2pf_offset; + uint32_t pf_csr_off = qat_pf2vf->pf2vf_offset; + int type_shift = qat_pf2vf->pf2vf_type_shift; + uint32_t type_mask = qat_pf2vf->pf2vf_type_mask; + int blck_hdr_shift = qat_pf2vf->pf2vf_data_shift; + int data_shift = blck_hdr_shift; + + switch (pf2vf_msg.msg_type) { + case ADF_VF2PF_MSGTYPE_GET_SMALL_BLOCK_REQ: + data_shift += ADF_VF2PF_SMALL_BLOCK_BYTE_NUM_SHIFT; + break; + case ADF_VF2PF_MSGTYPE_GET_MEDIUM_BLOCK_REQ: + data_shift += ADF_VF2PF_MEDIUM_BLOCK_BYTE_NUM_SHIFT; + break; + case ADF_VF2PF_MSGTYPE_GET_LARGE_BLOCK_REQ: + data_shift += ADF_VF2PF_LARGE_BLOCK_BYTE_NUM_SHIFT; + break; + } + + if ((pf2vf_msg.msg_type & type_mask) != pf2vf_msg.msg_type) { + QAT_LOG(ERR, "PF2VF message type 0x%X out of range\n", + pf2vf_msg.msg_type); + return -EINVAL; + } + + for (; i < len; i++) { + count = 0; + if (len == 1) { + msg = (pf2vf_msg.msg_type << type_shift) | + (pf2vf_msg.msg_data << (data_shift)); + } else + msg = (pf2vf_msg.msg_type << type_shift) | + ((pf2vf_msg.msg_data + i) << (data_shift)); + if (pf2vf_msg.block_hdr > 0) + msg |= pf2vf_msg.block_hdr << blck_hdr_shift; + msg |= ADF_PFVF_INT | ADF_PFVF_MSGORIGIN_SYSTEM; + + ADF_CSR_WR(pmisc_bar_addr, vf_csr_off, msg); + int us = 0; + /* + * Wait for confirmation from remote that it received + * the message + */ + do { + rte_delay_us_sleep(5); + us += 5; + val = ADF_CSR_RD(pmisc_bar_addr, vf_csr_off); + } while ((val & ADF_PFVF_INT) && + (++count < ADF_IOV_MSG_ACK_MAX_RETRY)); + + if (val & ADF_PFVF_INT) { + QAT_LOG(ERR, "ACK not received from remote\n"); + return -EIO; + } + + uint32_t pf_val = ADF_CSR_RD(pmisc_bar_addr, pf_csr_off); + + *(ret + i) = (uint8_t)(pf_val >> (pf2vf_msg.block_hdr > 0 ? + 10 : 8) & 0xff); + } + return 0; +} diff --git a/drivers/common/qat/qat_pf2vf.h b/drivers/common/qat/qat_pf2vf.h new file mode 100644 index 0000000000..df59277347 --- /dev/null +++ b/drivers/common/qat/qat_pf2vf.h @@ -0,0 +1,19 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2021 Intel Corporation + */ + +#include "qat_device.h" + +#ifndef QAT_PF2VF_H_ +#define QAT_PF2VF_H_ + +struct qat_pf2vf_msg { + uint32_t msg_data; + int block_hdr; + uint16_t msg_type; +}; + +int qat_pf2vf_exch_msg(struct qat_pci_device *qat_dev, + struct qat_pf2vf_msg pf2vf_msg, int len, uint8_t *ret); + +#endif -- 2.20.1