1 /* SPDX-License-Identifier: BSD-2-Clause */ 2 /* 3 * Copyright (c) 2022-2023, Huawei Technologies Co., Ltd 4 */ 5 #ifndef __HISI_QM_H__ 6 #define __HISI_QM_H__ 7 8 #include <io.h> 9 #include <kernel/delay.h> 10 #include <kernel/mutex.h> 11 #include <kernel/panic.h> 12 #include <mm/core_memprot.h> 13 #include <stdlib.h> 14 #include <string.h> 15 #include <string_ext.h> 16 #include <sys/queue.h> 17 18 #define HISI_QM_HW_V2 0x21 19 #define HISI_QM_HW_V3 0x30 20 #define HISI_QM_MAX_VFS_NUM 63 21 #define HISI_QM_PF_Q_BASE 0 22 #define HISI_QM_PF_Q_NUM 64 23 #define HISI_QM_VF_Q_NUM 15 24 #define HISI_QM_Q_DEPTH 8 25 #define PHASE_DEFAULT_VAL 0x1 26 27 #define HISI_QM_ABNML_INT_MASK 0x100004 28 #define HISI_QM_ABNML_INT_MASK_CFG 0x7fff 29 #define HISI_QM_ABNML_INT_SRC 0x100000 30 #define HISI_QM_HPRE_NFE_INT_MASK 0x6fb7 31 #define HISI_QM_SEC_NFE_INT_MASK 0x6ff7 32 #define HISI_QM_INVALID_DB BIT(12) 33 #define HISI_QM_REVISON_ID_BASE 0x1000dc 34 #define HISI_QM_REVISON_ID_MASK GENMASK_32(7, 0) 35 #define POLL_PERIOD 10 36 #define POLL_TIMEOUT 1000 37 #define HISI_QM_RECV_SYNC_TIMEOUT 0xfffff 38 #define HISI_QM_ALIGN128 128 39 #define HISI_QM_ALIGN32 32 40 #define QM_SINGLE_WAIT_TIME 5 41 #define ADDR_U64(upper, lower) ((uint64_t)(upper) << 32 | (lower)) 42 43 enum qm_fun_type { 44 HISI_QM_HW_PF, 45 HISI_QM_HW_VF, 46 }; 47 48 enum qm_sq_type { 49 HISI_QM_CHANNEL_TYPE0 = 0, 50 HISI_QM_CHANNEL_TYPE1, 51 HISI_QM_CHANNEL_TYPE2, 52 }; 53 54 struct qm_sqc { 55 uint16_t head; 56 uint16_t tail; 57 uint32_t base_l; 58 uint32_t base_h; 59 /* 60 * qes : 12 61 * sqe : 4 62 * rsv(stash_nid/stash_en) : 16 63 */ 64 uint32_t dw3; 65 uint16_t rand_data; 66 uint16_t rsv0; 67 uint16_t pasid; 68 /* 69 * rsv : 5 70 * head_sig : 1 71 * tail_sig : 1 72 * pasid_en : 1 73 * rsv : 8 74 */ 75 uint16_t w11; 76 uint16_t cq_num; 77 /* 78 * priority(Credit): 4 79 * order(order/fc/close/rsv) : 4 80 * type : 4 81 * rsv : 4 82 */ 83 uint16_t w13; 84 uint32_t rsv1; 85 }; 86 87 struct qm_cqc { 88 uint16_t head; 89 uint16_t tail; 90 uint32_t base_l; 91 uint32_t base_h; 92 /* 93 * qes : 12 94 * cqe_size : 4 95 * rsv(stash_nid/stash_en) : 16 96 */ 97 uint32_t dw3; 98 uint16_t rand_data; 99 uint16_t rsv0; 100 uint16_t pasid; 101 /* 102 * pasid_en : 1 103 * rsv : 4 104 * head_sig : 1 105 * tail_sig : 1 106 * rsv : 9 107 */ 108 uint16_t w11; 109 /* 110 * phase : 1 111 * c_flag : 1 112 * stash_vld : 1 113 */ 114 uint32_t dw6; 115 uint32_t rsv1; 116 }; 117 118 struct qm_cqe { 119 uint32_t rsv0; 120 uint16_t cmd_id; 121 uint16_t rsv1; 122 uint16_t sq_head; 123 uint16_t sq_id; 124 uint16_t rsv2; 125 /* 126 * p : 1 127 * status : 15 128 */ 129 uint16_t w7; 130 }; 131 132 struct hisi_qp { 133 struct hisi_qm *qm; 134 uint32_t qp_id; 135 uint8_t sq_type; 136 uint16_t sq_tail; 137 uint16_t cq_head; 138 bool cqc_phase; 139 bool used; 140 141 void *sqe; 142 struct qm_cqe *cqe; 143 paddr_t sqe_dma; 144 paddr_t cqe_dma; 145 146 enum hisi_drv_status (*fill_sqe)(void *sqe, void *msg); 147 enum hisi_drv_status (*parse_sqe)(void *sqe, void *msg); 148 }; 149 150 struct qm_xqc { 151 struct qm_sqc *sqc; 152 struct qm_cqc *cqc; 153 paddr_t sqc_dma; 154 paddr_t cqc_dma; 155 }; 156 157 struct hisi_qm { 158 enum qm_fun_type fun_type; 159 vaddr_t io_base; 160 uint32_t io_size; 161 uint32_t vfs_num; 162 uint32_t version; 163 164 struct qm_xqc xqc; 165 struct qm_xqc cfg_xqc; 166 uint32_t sqe_size; 167 uint32_t sqe_log2_size; 168 uint32_t qp_base; 169 uint32_t qp_num; 170 uint32_t qp_in_used; 171 uint32_t qp_idx; 172 struct hisi_qp *qp_array; 173 struct mutex qp_lock; /* protect the qp instance */ 174 struct mutex mailbox_lock; 175 176 enum hisi_drv_status (*dev_status_check)(struct hisi_qm *qm); 177 }; 178 179 enum hisi_drv_status { 180 HISI_QM_DRVCRYPT_NO_ERR = 0, 181 HISI_QM_DRVCRYPT_FAIL = 1, 182 HISI_QM_DRVCRYPT_EIO = 5, 183 HISI_QM_DRVCRYPT_EAGAIN = 11, 184 HISI_QM_DRVCRYPT_ENOMEM = 12, 185 HISI_QM_DRVCRYPT_EFAULT = 14, 186 HISI_QM_DRVCRYPT_EBUSY = 16, 187 HISI_QM_DRVCRYPT_ENODEV = 19, 188 HISI_QM_DRVCRYPT_EINVAL = 22, 189 HISI_QM_DRVCRYPT_ETMOUT = 110, 190 HISI_QM_DRVCRYPT_RECV_DONE = 175, 191 HISI_QM_DRVCRYPT_ENOPROC, 192 HISI_QM_DRVCRYPT_IN_EPARA, 193 HISI_QM_DRVCRYPT_VERIFY_ERR, 194 HISI_QM_DRVCRYPT_HW_EACCESS, 195 }; 196 197 struct acc_device { 198 struct hisi_qm qm; 199 vaddr_t io_base; 200 uint32_t io_size; 201 uint32_t vfs_num; 202 uint32_t endian; 203 enum qm_fun_type fun_type; 204 SLIST_ENTRY(acc_device) link; 205 }; 206 207 /** 208 * @Description: Get the version information of QM hardware 209 * @param qm: Handle of Queue Management module 210 */ 211 void hisi_qm_get_version(struct hisi_qm *qm); 212 213 /** 214 * @Description: Init QM for Kunpeng drv 215 * @param qm: Handle of Queue Management module 216 * @return success: HISI_QM_DRVCRYPT_NO_ERR, 217 * fail: HISI_QM_DRVCRYPT_EBUSY/HISI_QM_DRVCRYPT_EINVAL 218 */ 219 enum hisi_drv_status hisi_qm_init(struct hisi_qm *qm); 220 221 /** 222 * @Description:deinit QM for Kunpeng drv 223 * @param qm: Handle of Queue Management module 224 */ 225 void hisi_qm_uninit(struct hisi_qm *qm); 226 227 /** 228 * @Description: Start QM for Kunpeng drv 229 * @param qm: Handle of Queue Management module 230 */ 231 enum hisi_drv_status hisi_qm_start(struct hisi_qm *qm); 232 233 /** 234 * @Description: Config QM for Kunpeng drv 235 * @param qm: Handle of Queue Management module 236 */ 237 void hisi_qm_dev_init(struct hisi_qm *qm); 238 239 /** 240 * @Description: Create Queue Pair, allocated to PF/VF for configure 241 * and service use. Each QP includes one SQ and one CQ 242 * @param qm: Handle of Queue Management module 243 * @param sq_type: Accelerator specific algorithm type in sqc 244 * @return success: Handle of QP,fail: NULL 245 */ 246 struct hisi_qp *hisi_qm_create_qp(struct hisi_qm *qm, uint8_t sq_type); 247 248 /** 249 * @Description:Release Queue Pair 250 * @param qp: Handle of Queue Pair 251 */ 252 void hisi_qm_release_qp(struct hisi_qp *qp); 253 254 /** 255 * @Description: Send SQE(Submmision Queue Element) to Kunpeng dev 256 * @param qp: Handle of Queue Pair 257 * @param msg: The message 258 * @return success: HISI_QM_DRVCRYPT_NO_ERR,fail: HISI_QM_DRVCRYPT_EINVAL 259 */ 260 enum hisi_drv_status hisi_qp_send(struct hisi_qp *qp, void *msg); 261 262 /** 263 * @Description: Recevice result from Kunpeng dev 264 * @param qp: Handle of Queue Pair 265 * @param msg: The message 266 * @return success: HISI_QM_DRVCRYPT_NO_ERR 267 * fail: HISI_QM_DRVCRYPT_EINVAL/ETMOUT 268 */ 269 enum hisi_drv_status hisi_qp_recv_sync(struct hisi_qp *qp, void *msg); 270 271 #endif 272