1*cdcd52d4SBartosz Sobczak /*- 2*cdcd52d4SBartosz Sobczak * SPDX-License-Identifier: GPL-2.0 or Linux-OpenIB 3*cdcd52d4SBartosz Sobczak * 4*cdcd52d4SBartosz Sobczak * Copyright (c) 2015 - 2022 Intel Corporation 5*cdcd52d4SBartosz Sobczak * 6*cdcd52d4SBartosz Sobczak * This software is available to you under a choice of one of two 7*cdcd52d4SBartosz Sobczak * licenses. You may choose to be licensed under the terms of the GNU 8*cdcd52d4SBartosz Sobczak * General Public License (GPL) Version 2, available from the file 9*cdcd52d4SBartosz Sobczak * COPYING in the main directory of this source tree, or the 10*cdcd52d4SBartosz Sobczak * OpenFabrics.org BSD license below: 11*cdcd52d4SBartosz Sobczak * 12*cdcd52d4SBartosz Sobczak * Redistribution and use in source and binary forms, with or 13*cdcd52d4SBartosz Sobczak * without modification, are permitted provided that the following 14*cdcd52d4SBartosz Sobczak * conditions are met: 15*cdcd52d4SBartosz Sobczak * 16*cdcd52d4SBartosz Sobczak * - Redistributions of source code must retain the above 17*cdcd52d4SBartosz Sobczak * copyright notice, this list of conditions and the following 18*cdcd52d4SBartosz Sobczak * disclaimer. 19*cdcd52d4SBartosz Sobczak * 20*cdcd52d4SBartosz Sobczak * - Redistributions in binary form must reproduce the above 21*cdcd52d4SBartosz Sobczak * copyright notice, this list of conditions and the following 22*cdcd52d4SBartosz Sobczak * disclaimer in the documentation and/or other materials 23*cdcd52d4SBartosz Sobczak * provided with the distribution. 24*cdcd52d4SBartosz Sobczak * 25*cdcd52d4SBartosz Sobczak * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 26*cdcd52d4SBartosz Sobczak * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 27*cdcd52d4SBartosz Sobczak * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 28*cdcd52d4SBartosz Sobczak * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS 29*cdcd52d4SBartosz Sobczak * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN 30*cdcd52d4SBartosz Sobczak * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 31*cdcd52d4SBartosz Sobczak * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 32*cdcd52d4SBartosz Sobczak * SOFTWARE. 33*cdcd52d4SBartosz Sobczak */ 34*cdcd52d4SBartosz Sobczak /*$FreeBSD$*/ 35*cdcd52d4SBartosz Sobczak 36*cdcd52d4SBartosz Sobczak #include "osdep.h" 37*cdcd52d4SBartosz Sobczak #include "irdma_hmc.h" 38*cdcd52d4SBartosz Sobczak #include "irdma_defs.h" 39*cdcd52d4SBartosz Sobczak #include "irdma_type.h" 40*cdcd52d4SBartosz Sobczak #include "irdma_ws.h" 41*cdcd52d4SBartosz Sobczak #include "irdma_protos.h" 42*cdcd52d4SBartosz Sobczak 43*cdcd52d4SBartosz Sobczak /** 44*cdcd52d4SBartosz Sobczak * irdma_qp_from_entry - Given entry, get to the qp structure 45*cdcd52d4SBartosz Sobczak * @entry: Points to list of qp structure 46*cdcd52d4SBartosz Sobczak */ 47*cdcd52d4SBartosz Sobczak static struct irdma_sc_qp * 48*cdcd52d4SBartosz Sobczak irdma_qp_from_entry(struct list_head *entry) 49*cdcd52d4SBartosz Sobczak { 50*cdcd52d4SBartosz Sobczak if (!entry) 51*cdcd52d4SBartosz Sobczak return NULL; 52*cdcd52d4SBartosz Sobczak 53*cdcd52d4SBartosz Sobczak return (struct irdma_sc_qp *)((char *)entry - 54*cdcd52d4SBartosz Sobczak offsetof(struct irdma_sc_qp, list)); 55*cdcd52d4SBartosz Sobczak } 56*cdcd52d4SBartosz Sobczak 57*cdcd52d4SBartosz Sobczak /** 58*cdcd52d4SBartosz Sobczak * irdma_get_qp_from_list - get next qp from a list 59*cdcd52d4SBartosz Sobczak * @head: Listhead of qp's 60*cdcd52d4SBartosz Sobczak * @qp: current qp 61*cdcd52d4SBartosz Sobczak */ 62*cdcd52d4SBartosz Sobczak struct irdma_sc_qp * 63*cdcd52d4SBartosz Sobczak irdma_get_qp_from_list(struct list_head *head, 64*cdcd52d4SBartosz Sobczak struct irdma_sc_qp *qp) 65*cdcd52d4SBartosz Sobczak { 66*cdcd52d4SBartosz Sobczak struct list_head *lastentry; 67*cdcd52d4SBartosz Sobczak struct list_head *entry = NULL; 68*cdcd52d4SBartosz Sobczak 69*cdcd52d4SBartosz Sobczak if (list_empty(head)) 70*cdcd52d4SBartosz Sobczak return NULL; 71*cdcd52d4SBartosz Sobczak 72*cdcd52d4SBartosz Sobczak if (!qp) { 73*cdcd52d4SBartosz Sobczak entry = (head)->next; 74*cdcd52d4SBartosz Sobczak } else { 75*cdcd52d4SBartosz Sobczak lastentry = &qp->list; 76*cdcd52d4SBartosz Sobczak entry = (lastentry)->next; 77*cdcd52d4SBartosz Sobczak if (entry == head) 78*cdcd52d4SBartosz Sobczak return NULL; 79*cdcd52d4SBartosz Sobczak } 80*cdcd52d4SBartosz Sobczak 81*cdcd52d4SBartosz Sobczak return irdma_qp_from_entry(entry); 82*cdcd52d4SBartosz Sobczak } 83*cdcd52d4SBartosz Sobczak 84*cdcd52d4SBartosz Sobczak /** 85*cdcd52d4SBartosz Sobczak * irdma_sc_suspend_resume_qps - suspend/resume all qp's on VSI 86*cdcd52d4SBartosz Sobczak * @vsi: the VSI struct pointer 87*cdcd52d4SBartosz Sobczak * @op: Set to IRDMA_OP_RESUME or IRDMA_OP_SUSPEND 88*cdcd52d4SBartosz Sobczak */ 89*cdcd52d4SBartosz Sobczak void 90*cdcd52d4SBartosz Sobczak irdma_sc_suspend_resume_qps(struct irdma_sc_vsi *vsi, u8 op) 91*cdcd52d4SBartosz Sobczak { 92*cdcd52d4SBartosz Sobczak struct irdma_sc_qp *qp = NULL; 93*cdcd52d4SBartosz Sobczak u8 i; 94*cdcd52d4SBartosz Sobczak 95*cdcd52d4SBartosz Sobczak for (i = 0; i < IRDMA_MAX_USER_PRIORITY; i++) { 96*cdcd52d4SBartosz Sobczak mutex_lock(&vsi->qos[i].qos_mutex); 97*cdcd52d4SBartosz Sobczak qp = irdma_get_qp_from_list(&vsi->qos[i].qplist, qp); 98*cdcd52d4SBartosz Sobczak while (qp) { 99*cdcd52d4SBartosz Sobczak if (op == IRDMA_OP_RESUME) { 100*cdcd52d4SBartosz Sobczak if (!qp->dev->ws_add(vsi, i)) { 101*cdcd52d4SBartosz Sobczak qp->qs_handle = 102*cdcd52d4SBartosz Sobczak vsi->qos[qp->user_pri].qs_handle; 103*cdcd52d4SBartosz Sobczak irdma_cqp_qp_suspend_resume(qp, op); 104*cdcd52d4SBartosz Sobczak } else { 105*cdcd52d4SBartosz Sobczak irdma_cqp_qp_suspend_resume(qp, op); 106*cdcd52d4SBartosz Sobczak irdma_modify_qp_to_err(qp); 107*cdcd52d4SBartosz Sobczak } 108*cdcd52d4SBartosz Sobczak } else if (op == IRDMA_OP_SUSPEND) { 109*cdcd52d4SBartosz Sobczak /* issue cqp suspend command */ 110*cdcd52d4SBartosz Sobczak if (!irdma_cqp_qp_suspend_resume(qp, op)) 111*cdcd52d4SBartosz Sobczak atomic_inc(&vsi->qp_suspend_reqs); 112*cdcd52d4SBartosz Sobczak } 113*cdcd52d4SBartosz Sobczak qp = irdma_get_qp_from_list(&vsi->qos[i].qplist, qp); 114*cdcd52d4SBartosz Sobczak } 115*cdcd52d4SBartosz Sobczak mutex_unlock(&vsi->qos[i].qos_mutex); 116*cdcd52d4SBartosz Sobczak } 117*cdcd52d4SBartosz Sobczak } 118*cdcd52d4SBartosz Sobczak 119*cdcd52d4SBartosz Sobczak static void 120*cdcd52d4SBartosz Sobczak irdma_set_qos_info(struct irdma_sc_vsi *vsi, struct irdma_l2params *l2p) 121*cdcd52d4SBartosz Sobczak { 122*cdcd52d4SBartosz Sobczak u8 i; 123*cdcd52d4SBartosz Sobczak 124*cdcd52d4SBartosz Sobczak vsi->qos_rel_bw = l2p->vsi_rel_bw; 125*cdcd52d4SBartosz Sobczak vsi->qos_prio_type = l2p->vsi_prio_type; 126*cdcd52d4SBartosz Sobczak vsi->dscp_mode = l2p->dscp_mode; 127*cdcd52d4SBartosz Sobczak if (l2p->dscp_mode) { 128*cdcd52d4SBartosz Sobczak irdma_memcpy(vsi->dscp_map, l2p->dscp_map, sizeof(vsi->dscp_map)); 129*cdcd52d4SBartosz Sobczak for (i = 0; i < IRDMA_MAX_USER_PRIORITY; i++) 130*cdcd52d4SBartosz Sobczak l2p->up2tc[i] = i; 131*cdcd52d4SBartosz Sobczak } 132*cdcd52d4SBartosz Sobczak for (i = 0; i < IRDMA_MAX_TRAFFIC_CLASS; i++) 133*cdcd52d4SBartosz Sobczak vsi->tc_print_warning[i] = true; 134*cdcd52d4SBartosz Sobczak for (i = 0; i < IRDMA_MAX_USER_PRIORITY; i++) { 135*cdcd52d4SBartosz Sobczak if (vsi->dev->hw_attrs.uk_attrs.hw_rev == IRDMA_GEN_1) 136*cdcd52d4SBartosz Sobczak vsi->qos[i].qs_handle = l2p->qs_handle_list[i]; 137*cdcd52d4SBartosz Sobczak if (vsi->dev->hw_attrs.uk_attrs.hw_rev == IRDMA_GEN_2) 138*cdcd52d4SBartosz Sobczak irdma_init_config_check(&vsi->cfg_check[i], 139*cdcd52d4SBartosz Sobczak l2p->up2tc[i], 140*cdcd52d4SBartosz Sobczak l2p->qs_handle_list[i]); 141*cdcd52d4SBartosz Sobczak vsi->qos[i].traffic_class = l2p->up2tc[i]; 142*cdcd52d4SBartosz Sobczak vsi->qos[i].rel_bw = 143*cdcd52d4SBartosz Sobczak l2p->tc_info[vsi->qos[i].traffic_class].rel_bw; 144*cdcd52d4SBartosz Sobczak vsi->qos[i].prio_type = 145*cdcd52d4SBartosz Sobczak l2p->tc_info[vsi->qos[i].traffic_class].prio_type; 146*cdcd52d4SBartosz Sobczak vsi->qos[i].valid = false; 147*cdcd52d4SBartosz Sobczak } 148*cdcd52d4SBartosz Sobczak } 149*cdcd52d4SBartosz Sobczak 150*cdcd52d4SBartosz Sobczak /** 151*cdcd52d4SBartosz Sobczak * irdma_change_l2params - given the new l2 parameters, change all qp 152*cdcd52d4SBartosz Sobczak * @vsi: RDMA VSI pointer 153*cdcd52d4SBartosz Sobczak * @l2params: New parameters from l2 154*cdcd52d4SBartosz Sobczak */ 155*cdcd52d4SBartosz Sobczak void 156*cdcd52d4SBartosz Sobczak irdma_change_l2params(struct irdma_sc_vsi *vsi, 157*cdcd52d4SBartosz Sobczak struct irdma_l2params *l2params) 158*cdcd52d4SBartosz Sobczak { 159*cdcd52d4SBartosz Sobczak if (l2params->mtu_changed) { 160*cdcd52d4SBartosz Sobczak vsi->mtu = l2params->mtu; 161*cdcd52d4SBartosz Sobczak if (vsi->ieq) 162*cdcd52d4SBartosz Sobczak irdma_reinitialize_ieq(vsi); 163*cdcd52d4SBartosz Sobczak } 164*cdcd52d4SBartosz Sobczak 165*cdcd52d4SBartosz Sobczak if (!l2params->tc_changed) 166*cdcd52d4SBartosz Sobczak return; 167*cdcd52d4SBartosz Sobczak 168*cdcd52d4SBartosz Sobczak vsi->tc_change_pending = false; 169*cdcd52d4SBartosz Sobczak irdma_set_qos_info(vsi, l2params); 170*cdcd52d4SBartosz Sobczak irdma_sc_suspend_resume_qps(vsi, IRDMA_OP_RESUME); 171*cdcd52d4SBartosz Sobczak } 172*cdcd52d4SBartosz Sobczak 173*cdcd52d4SBartosz Sobczak /** 174*cdcd52d4SBartosz Sobczak * irdma_qp_rem_qos - remove qp from qos lists during destroy qp 175*cdcd52d4SBartosz Sobczak * @qp: qp to be removed from qos 176*cdcd52d4SBartosz Sobczak */ 177*cdcd52d4SBartosz Sobczak void 178*cdcd52d4SBartosz Sobczak irdma_qp_rem_qos(struct irdma_sc_qp *qp) 179*cdcd52d4SBartosz Sobczak { 180*cdcd52d4SBartosz Sobczak struct irdma_sc_vsi *vsi = qp->vsi; 181*cdcd52d4SBartosz Sobczak 182*cdcd52d4SBartosz Sobczak irdma_debug(qp->dev, IRDMA_DEBUG_DCB, 183*cdcd52d4SBartosz Sobczak "DCB: Remove qp[%d] UP[%d] qset[%d] on_qoslist[%d]\n", 184*cdcd52d4SBartosz Sobczak qp->qp_uk.qp_id, qp->user_pri, qp->qs_handle, qp->on_qoslist); 185*cdcd52d4SBartosz Sobczak mutex_lock(&vsi->qos[qp->user_pri].qos_mutex); 186*cdcd52d4SBartosz Sobczak if (qp->on_qoslist) { 187*cdcd52d4SBartosz Sobczak qp->on_qoslist = false; 188*cdcd52d4SBartosz Sobczak list_del(&qp->list); 189*cdcd52d4SBartosz Sobczak } 190*cdcd52d4SBartosz Sobczak mutex_unlock(&vsi->qos[qp->user_pri].qos_mutex); 191*cdcd52d4SBartosz Sobczak } 192*cdcd52d4SBartosz Sobczak 193*cdcd52d4SBartosz Sobczak /** 194*cdcd52d4SBartosz Sobczak * irdma_qp_add_qos - called during setctx for qp to be added to qos 195*cdcd52d4SBartosz Sobczak * @qp: qp to be added to qos 196*cdcd52d4SBartosz Sobczak */ 197*cdcd52d4SBartosz Sobczak void 198*cdcd52d4SBartosz Sobczak irdma_qp_add_qos(struct irdma_sc_qp *qp) 199*cdcd52d4SBartosz Sobczak { 200*cdcd52d4SBartosz Sobczak struct irdma_sc_vsi *vsi = qp->vsi; 201*cdcd52d4SBartosz Sobczak 202*cdcd52d4SBartosz Sobczak irdma_debug(qp->dev, IRDMA_DEBUG_DCB, 203*cdcd52d4SBartosz Sobczak "DCB: Add qp[%d] UP[%d] qset[%d] on_qoslist[%d]\n", 204*cdcd52d4SBartosz Sobczak qp->qp_uk.qp_id, qp->user_pri, qp->qs_handle, qp->on_qoslist); 205*cdcd52d4SBartosz Sobczak mutex_lock(&vsi->qos[qp->user_pri].qos_mutex); 206*cdcd52d4SBartosz Sobczak if (!qp->on_qoslist) { 207*cdcd52d4SBartosz Sobczak list_add(&qp->list, &vsi->qos[qp->user_pri].qplist); 208*cdcd52d4SBartosz Sobczak qp->on_qoslist = true; 209*cdcd52d4SBartosz Sobczak qp->qs_handle = vsi->qos[qp->user_pri].qs_handle; 210*cdcd52d4SBartosz Sobczak } 211*cdcd52d4SBartosz Sobczak mutex_unlock(&vsi->qos[qp->user_pri].qos_mutex); 212*cdcd52d4SBartosz Sobczak } 213*cdcd52d4SBartosz Sobczak 214*cdcd52d4SBartosz Sobczak /** 215*cdcd52d4SBartosz Sobczak * irdma_sc_pd_init - initialize sc pd struct 216*cdcd52d4SBartosz Sobczak * @dev: sc device struct 217*cdcd52d4SBartosz Sobczak * @pd: sc pd ptr 218*cdcd52d4SBartosz Sobczak * @pd_id: pd_id for allocated pd 219*cdcd52d4SBartosz Sobczak * @abi_ver: User/Kernel ABI version 220*cdcd52d4SBartosz Sobczak */ 221*cdcd52d4SBartosz Sobczak void 222*cdcd52d4SBartosz Sobczak irdma_sc_pd_init(struct irdma_sc_dev *dev, struct irdma_sc_pd *pd, u32 pd_id, 223*cdcd52d4SBartosz Sobczak int abi_ver) 224*cdcd52d4SBartosz Sobczak { 225*cdcd52d4SBartosz Sobczak pd->pd_id = pd_id; 226*cdcd52d4SBartosz Sobczak pd->abi_ver = abi_ver; 227*cdcd52d4SBartosz Sobczak pd->dev = dev; 228*cdcd52d4SBartosz Sobczak } 229*cdcd52d4SBartosz Sobczak 230*cdcd52d4SBartosz Sobczak /** 231*cdcd52d4SBartosz Sobczak * irdma_sc_add_arp_cache_entry - cqp wqe add arp cache entry 232*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 233*cdcd52d4SBartosz Sobczak * @info: arp entry information 234*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 235*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 236*cdcd52d4SBartosz Sobczak */ 237*cdcd52d4SBartosz Sobczak static int 238*cdcd52d4SBartosz Sobczak irdma_sc_add_arp_cache_entry(struct irdma_sc_cqp *cqp, 239*cdcd52d4SBartosz Sobczak struct irdma_add_arp_cache_entry_info *info, 240*cdcd52d4SBartosz Sobczak u64 scratch, bool post_sq) 241*cdcd52d4SBartosz Sobczak { 242*cdcd52d4SBartosz Sobczak __le64 *wqe; 243*cdcd52d4SBartosz Sobczak u64 temp, hdr; 244*cdcd52d4SBartosz Sobczak 245*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 246*cdcd52d4SBartosz Sobczak if (!wqe) 247*cdcd52d4SBartosz Sobczak return -ENOSPC; 248*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, info->reach_max); 249*cdcd52d4SBartosz Sobczak 250*cdcd52d4SBartosz Sobczak temp = info->mac_addr[5] | LS_64_1(info->mac_addr[4], 8) | 251*cdcd52d4SBartosz Sobczak LS_64_1(info->mac_addr[3], 16) | LS_64_1(info->mac_addr[2], 24) | 252*cdcd52d4SBartosz Sobczak LS_64_1(info->mac_addr[1], 32) | LS_64_1(info->mac_addr[0], 40); 253*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, temp); 254*cdcd52d4SBartosz Sobczak 255*cdcd52d4SBartosz Sobczak hdr = info->arp_index | 256*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_MANAGE_ARP, IRDMA_CQPSQ_OPCODE) | 257*cdcd52d4SBartosz Sobczak LS_64((info->permanent ? 1 : 0), IRDMA_CQPSQ_MAT_PERMANENT) | 258*cdcd52d4SBartosz Sobczak LS_64(1, IRDMA_CQPSQ_MAT_ENTRYVALID) | 259*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 260*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 261*cdcd52d4SBartosz Sobczak 262*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 263*cdcd52d4SBartosz Sobczak 264*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "ARP_CACHE_ENTRY WQE", wqe, 265*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 266*cdcd52d4SBartosz Sobczak if (post_sq) 267*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 268*cdcd52d4SBartosz Sobczak 269*cdcd52d4SBartosz Sobczak return 0; 270*cdcd52d4SBartosz Sobczak } 271*cdcd52d4SBartosz Sobczak 272*cdcd52d4SBartosz Sobczak /** 273*cdcd52d4SBartosz Sobczak * irdma_sc_del_arp_cache_entry - dele arp cache entry 274*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 275*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 276*cdcd52d4SBartosz Sobczak * @arp_index: arp index to delete arp entry 277*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 278*cdcd52d4SBartosz Sobczak */ 279*cdcd52d4SBartosz Sobczak static int 280*cdcd52d4SBartosz Sobczak irdma_sc_del_arp_cache_entry(struct irdma_sc_cqp *cqp, u64 scratch, 281*cdcd52d4SBartosz Sobczak u16 arp_index, bool post_sq) 282*cdcd52d4SBartosz Sobczak { 283*cdcd52d4SBartosz Sobczak __le64 *wqe; 284*cdcd52d4SBartosz Sobczak u64 hdr; 285*cdcd52d4SBartosz Sobczak 286*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 287*cdcd52d4SBartosz Sobczak if (!wqe) 288*cdcd52d4SBartosz Sobczak return -ENOSPC; 289*cdcd52d4SBartosz Sobczak 290*cdcd52d4SBartosz Sobczak hdr = arp_index | LS_64(IRDMA_CQP_OP_MANAGE_ARP, IRDMA_CQPSQ_OPCODE) | 291*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 292*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 293*cdcd52d4SBartosz Sobczak 294*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 295*cdcd52d4SBartosz Sobczak 296*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "ARP_CACHE_DEL_ENTRY WQE", 297*cdcd52d4SBartosz Sobczak wqe, IRDMA_CQP_WQE_SIZE * 8); 298*cdcd52d4SBartosz Sobczak if (post_sq) 299*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 300*cdcd52d4SBartosz Sobczak 301*cdcd52d4SBartosz Sobczak return 0; 302*cdcd52d4SBartosz Sobczak } 303*cdcd52d4SBartosz Sobczak 304*cdcd52d4SBartosz Sobczak /** 305*cdcd52d4SBartosz Sobczak * irdma_sc_manage_apbvt_entry - for adding and deleting apbvt entries 306*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 307*cdcd52d4SBartosz Sobczak * @info: info for apbvt entry to add or delete 308*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 309*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 310*cdcd52d4SBartosz Sobczak */ 311*cdcd52d4SBartosz Sobczak static int 312*cdcd52d4SBartosz Sobczak irdma_sc_manage_apbvt_entry(struct irdma_sc_cqp *cqp, 313*cdcd52d4SBartosz Sobczak struct irdma_apbvt_info *info, 314*cdcd52d4SBartosz Sobczak u64 scratch, bool post_sq) 315*cdcd52d4SBartosz Sobczak { 316*cdcd52d4SBartosz Sobczak __le64 *wqe; 317*cdcd52d4SBartosz Sobczak u64 hdr; 318*cdcd52d4SBartosz Sobczak 319*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 320*cdcd52d4SBartosz Sobczak if (!wqe) 321*cdcd52d4SBartosz Sobczak return -ENOSPC; 322*cdcd52d4SBartosz Sobczak 323*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, info->port); 324*cdcd52d4SBartosz Sobczak 325*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMA_CQP_OP_MANAGE_APBVT, IRDMA_CQPSQ_OPCODE) | 326*cdcd52d4SBartosz Sobczak LS_64(info->add, IRDMA_CQPSQ_MAPT_ADDPORT) | 327*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 328*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 329*cdcd52d4SBartosz Sobczak 330*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 331*cdcd52d4SBartosz Sobczak 332*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "MANAGE_APBVT WQE", wqe, 333*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 334*cdcd52d4SBartosz Sobczak if (post_sq) 335*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 336*cdcd52d4SBartosz Sobczak 337*cdcd52d4SBartosz Sobczak return 0; 338*cdcd52d4SBartosz Sobczak } 339*cdcd52d4SBartosz Sobczak 340*cdcd52d4SBartosz Sobczak /** 341*cdcd52d4SBartosz Sobczak * irdma_sc_manage_qhash_table_entry - manage quad hash entries 342*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 343*cdcd52d4SBartosz Sobczak * @info: info for quad hash to manage 344*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 345*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 346*cdcd52d4SBartosz Sobczak * 347*cdcd52d4SBartosz Sobczak * This is called before connection establishment is started. 348*cdcd52d4SBartosz Sobczak * For passive connections, when listener is created, it will 349*cdcd52d4SBartosz Sobczak * call with entry type of IRDMA_QHASH_TYPE_TCP_SYN with local 350*cdcd52d4SBartosz Sobczak * ip address and tcp port. When SYN is received (passive 351*cdcd52d4SBartosz Sobczak * connections) or sent (active connections), this routine is 352*cdcd52d4SBartosz Sobczak * called with entry type of IRDMA_QHASH_TYPE_TCP_ESTABLISHED 353*cdcd52d4SBartosz Sobczak * and quad is passed in info. 354*cdcd52d4SBartosz Sobczak * 355*cdcd52d4SBartosz Sobczak * When iwarp connection is done and its state moves to RTS, the 356*cdcd52d4SBartosz Sobczak * quad hash entry in the hardware will point to iwarp's qp 357*cdcd52d4SBartosz Sobczak * number and requires no calls from the driver. 358*cdcd52d4SBartosz Sobczak */ 359*cdcd52d4SBartosz Sobczak static int 360*cdcd52d4SBartosz Sobczak irdma_sc_manage_qhash_table_entry(struct irdma_sc_cqp *cqp, 361*cdcd52d4SBartosz Sobczak struct irdma_qhash_table_info *info, 362*cdcd52d4SBartosz Sobczak u64 scratch, bool post_sq) 363*cdcd52d4SBartosz Sobczak { 364*cdcd52d4SBartosz Sobczak __le64 *wqe; 365*cdcd52d4SBartosz Sobczak u64 qw1 = 0; 366*cdcd52d4SBartosz Sobczak u64 qw2 = 0; 367*cdcd52d4SBartosz Sobczak u64 temp; 368*cdcd52d4SBartosz Sobczak struct irdma_sc_vsi *vsi = info->vsi; 369*cdcd52d4SBartosz Sobczak 370*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 371*cdcd52d4SBartosz Sobczak if (!wqe) 372*cdcd52d4SBartosz Sobczak return -ENOSPC; 373*cdcd52d4SBartosz Sobczak temp = info->mac_addr[5] | LS_64_1(info->mac_addr[4], 8) | 374*cdcd52d4SBartosz Sobczak LS_64_1(info->mac_addr[3], 16) | LS_64_1(info->mac_addr[2], 24) | 375*cdcd52d4SBartosz Sobczak LS_64_1(info->mac_addr[1], 32) | LS_64_1(info->mac_addr[0], 40); 376*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_0, temp); 377*cdcd52d4SBartosz Sobczak 378*cdcd52d4SBartosz Sobczak qw1 = LS_64(info->qp_num, IRDMA_CQPSQ_QHASH_QPN) | 379*cdcd52d4SBartosz Sobczak LS_64(info->dest_port, IRDMA_CQPSQ_QHASH_DEST_PORT); 380*cdcd52d4SBartosz Sobczak if (info->ipv4_valid) { 381*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_48, 382*cdcd52d4SBartosz Sobczak LS_64(info->dest_ip[0], IRDMA_CQPSQ_QHASH_ADDR3)); 383*cdcd52d4SBartosz Sobczak } else { 384*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_56, 385*cdcd52d4SBartosz Sobczak LS_64(info->dest_ip[0], IRDMA_CQPSQ_QHASH_ADDR0) | 386*cdcd52d4SBartosz Sobczak LS_64(info->dest_ip[1], IRDMA_CQPSQ_QHASH_ADDR1)); 387*cdcd52d4SBartosz Sobczak 388*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_48, 389*cdcd52d4SBartosz Sobczak LS_64(info->dest_ip[2], IRDMA_CQPSQ_QHASH_ADDR2) | 390*cdcd52d4SBartosz Sobczak LS_64(info->dest_ip[3], IRDMA_CQPSQ_QHASH_ADDR3)); 391*cdcd52d4SBartosz Sobczak } 392*cdcd52d4SBartosz Sobczak qw2 = LS_64(vsi->qos[info->user_pri].qs_handle, 393*cdcd52d4SBartosz Sobczak IRDMA_CQPSQ_QHASH_QS_HANDLE); 394*cdcd52d4SBartosz Sobczak if (info->vlan_valid) 395*cdcd52d4SBartosz Sobczak qw2 |= LS_64(info->vlan_id, IRDMA_CQPSQ_QHASH_VLANID); 396*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, qw2); 397*cdcd52d4SBartosz Sobczak if (info->entry_type == IRDMA_QHASH_TYPE_TCP_ESTABLISHED) { 398*cdcd52d4SBartosz Sobczak qw1 |= LS_64(info->src_port, IRDMA_CQPSQ_QHASH_SRC_PORT); 399*cdcd52d4SBartosz Sobczak if (!info->ipv4_valid) { 400*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, 401*cdcd52d4SBartosz Sobczak LS_64(info->src_ip[0], IRDMA_CQPSQ_QHASH_ADDR0) | 402*cdcd52d4SBartosz Sobczak LS_64(info->src_ip[1], IRDMA_CQPSQ_QHASH_ADDR1)); 403*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, 404*cdcd52d4SBartosz Sobczak LS_64(info->src_ip[2], IRDMA_CQPSQ_QHASH_ADDR2) | 405*cdcd52d4SBartosz Sobczak LS_64(info->src_ip[3], IRDMA_CQPSQ_QHASH_ADDR3)); 406*cdcd52d4SBartosz Sobczak } else { 407*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, 408*cdcd52d4SBartosz Sobczak LS_64(info->src_ip[0], IRDMA_CQPSQ_QHASH_ADDR3)); 409*cdcd52d4SBartosz Sobczak } 410*cdcd52d4SBartosz Sobczak } 411*cdcd52d4SBartosz Sobczak 412*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, qw1); 413*cdcd52d4SBartosz Sobczak temp = LS_64(cqp->polarity, IRDMA_CQPSQ_QHASH_WQEVALID) | 414*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_MANAGE_QUAD_HASH_TABLE_ENTRY, 415*cdcd52d4SBartosz Sobczak IRDMA_CQPSQ_QHASH_OPCODE) | 416*cdcd52d4SBartosz Sobczak LS_64(info->manage, IRDMA_CQPSQ_QHASH_MANAGE) | 417*cdcd52d4SBartosz Sobczak LS_64(info->ipv4_valid, IRDMA_CQPSQ_QHASH_IPV4VALID) | 418*cdcd52d4SBartosz Sobczak LS_64(info->vlan_valid, IRDMA_CQPSQ_QHASH_VLANVALID) | 419*cdcd52d4SBartosz Sobczak LS_64(info->entry_type, IRDMA_CQPSQ_QHASH_ENTRYTYPE); 420*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 421*cdcd52d4SBartosz Sobczak 422*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, temp); 423*cdcd52d4SBartosz Sobczak 424*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "MANAGE_QHASH WQE", wqe, 425*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 426*cdcd52d4SBartosz Sobczak if (post_sq) 427*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 428*cdcd52d4SBartosz Sobczak 429*cdcd52d4SBartosz Sobczak return 0; 430*cdcd52d4SBartosz Sobczak } 431*cdcd52d4SBartosz Sobczak 432*cdcd52d4SBartosz Sobczak /** 433*cdcd52d4SBartosz Sobczak * irdma_sc_qp_init - initialize qp 434*cdcd52d4SBartosz Sobczak * @qp: sc qp 435*cdcd52d4SBartosz Sobczak * @info: initialization qp info 436*cdcd52d4SBartosz Sobczak */ 437*cdcd52d4SBartosz Sobczak int 438*cdcd52d4SBartosz Sobczak irdma_sc_qp_init(struct irdma_sc_qp *qp, struct irdma_qp_init_info *info) 439*cdcd52d4SBartosz Sobczak { 440*cdcd52d4SBartosz Sobczak int ret_code; 441*cdcd52d4SBartosz Sobczak u32 pble_obj_cnt; 442*cdcd52d4SBartosz Sobczak u16 wqe_size; 443*cdcd52d4SBartosz Sobczak 444*cdcd52d4SBartosz Sobczak if (info->qp_uk_init_info.max_sq_frag_cnt > 445*cdcd52d4SBartosz Sobczak info->pd->dev->hw_attrs.uk_attrs.max_hw_wq_frags || 446*cdcd52d4SBartosz Sobczak info->qp_uk_init_info.max_rq_frag_cnt > 447*cdcd52d4SBartosz Sobczak info->pd->dev->hw_attrs.uk_attrs.max_hw_wq_frags) 448*cdcd52d4SBartosz Sobczak return -EINVAL; 449*cdcd52d4SBartosz Sobczak 450*cdcd52d4SBartosz Sobczak qp->dev = info->pd->dev; 451*cdcd52d4SBartosz Sobczak qp->vsi = info->vsi; 452*cdcd52d4SBartosz Sobczak qp->ieq_qp = info->vsi->exception_lan_q; 453*cdcd52d4SBartosz Sobczak qp->sq_pa = info->sq_pa; 454*cdcd52d4SBartosz Sobczak qp->rq_pa = info->rq_pa; 455*cdcd52d4SBartosz Sobczak qp->hw_host_ctx_pa = info->host_ctx_pa; 456*cdcd52d4SBartosz Sobczak qp->q2_pa = info->q2_pa; 457*cdcd52d4SBartosz Sobczak qp->shadow_area_pa = info->shadow_area_pa; 458*cdcd52d4SBartosz Sobczak qp->q2_buf = info->q2; 459*cdcd52d4SBartosz Sobczak qp->pd = info->pd; 460*cdcd52d4SBartosz Sobczak qp->hw_host_ctx = info->host_ctx; 461*cdcd52d4SBartosz Sobczak info->qp_uk_init_info.wqe_alloc_db = qp->pd->dev->wqe_alloc_db; 462*cdcd52d4SBartosz Sobczak ret_code = irdma_uk_qp_init(&qp->qp_uk, &info->qp_uk_init_info); 463*cdcd52d4SBartosz Sobczak if (ret_code) 464*cdcd52d4SBartosz Sobczak return ret_code; 465*cdcd52d4SBartosz Sobczak 466*cdcd52d4SBartosz Sobczak qp->virtual_map = info->virtual_map; 467*cdcd52d4SBartosz Sobczak pble_obj_cnt = info->pd->dev->hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].cnt; 468*cdcd52d4SBartosz Sobczak 469*cdcd52d4SBartosz Sobczak if ((info->virtual_map && info->sq_pa >= pble_obj_cnt) || 470*cdcd52d4SBartosz Sobczak (info->virtual_map && info->rq_pa >= pble_obj_cnt)) 471*cdcd52d4SBartosz Sobczak return -EINVAL; 472*cdcd52d4SBartosz Sobczak 473*cdcd52d4SBartosz Sobczak qp->llp_stream_handle = (void *)(-1); 474*cdcd52d4SBartosz Sobczak qp->qp_uk.force_fence = true; 475*cdcd52d4SBartosz Sobczak qp->hw_sq_size = irdma_get_encoded_wqe_size(qp->qp_uk.sq_ring.size, 476*cdcd52d4SBartosz Sobczak IRDMA_QUEUE_TYPE_SQ_RQ); 477*cdcd52d4SBartosz Sobczak irdma_debug(qp->dev, IRDMA_DEBUG_WQE, 478*cdcd52d4SBartosz Sobczak "hw_sq_size[%04d] sq_ring.size[%04d]\n", qp->hw_sq_size, 479*cdcd52d4SBartosz Sobczak qp->qp_uk.sq_ring.size); 480*cdcd52d4SBartosz Sobczak if (qp->qp_uk.uk_attrs->hw_rev == IRDMA_GEN_1) 481*cdcd52d4SBartosz Sobczak wqe_size = IRDMA_WQE_SIZE_128; 482*cdcd52d4SBartosz Sobczak else 483*cdcd52d4SBartosz Sobczak ret_code = irdma_fragcnt_to_wqesize_rq(qp->qp_uk.max_rq_frag_cnt, 484*cdcd52d4SBartosz Sobczak &wqe_size); 485*cdcd52d4SBartosz Sobczak if (ret_code) 486*cdcd52d4SBartosz Sobczak return ret_code; 487*cdcd52d4SBartosz Sobczak 488*cdcd52d4SBartosz Sobczak qp->hw_rq_size = 489*cdcd52d4SBartosz Sobczak irdma_get_encoded_wqe_size(qp->qp_uk.rq_size * 490*cdcd52d4SBartosz Sobczak (wqe_size / IRDMA_QP_WQE_MIN_SIZE), 491*cdcd52d4SBartosz Sobczak IRDMA_QUEUE_TYPE_SQ_RQ); 492*cdcd52d4SBartosz Sobczak irdma_debug(qp->dev, IRDMA_DEBUG_WQE, 493*cdcd52d4SBartosz Sobczak "hw_rq_size[%04d] qp_uk.rq_size[%04d] wqe_size[%04d]\n", 494*cdcd52d4SBartosz Sobczak qp->hw_rq_size, qp->qp_uk.rq_size, wqe_size); 495*cdcd52d4SBartosz Sobczak 496*cdcd52d4SBartosz Sobczak qp->sq_tph_val = info->sq_tph_val; 497*cdcd52d4SBartosz Sobczak qp->rq_tph_val = info->rq_tph_val; 498*cdcd52d4SBartosz Sobczak qp->sq_tph_en = info->sq_tph_en; 499*cdcd52d4SBartosz Sobczak qp->rq_tph_en = info->rq_tph_en; 500*cdcd52d4SBartosz Sobczak qp->rcv_tph_en = info->rcv_tph_en; 501*cdcd52d4SBartosz Sobczak qp->xmit_tph_en = info->xmit_tph_en; 502*cdcd52d4SBartosz Sobczak qp->qp_uk.first_sq_wq = info->qp_uk_init_info.first_sq_wq; 503*cdcd52d4SBartosz Sobczak qp->qs_handle = qp->vsi->qos[qp->user_pri].qs_handle; 504*cdcd52d4SBartosz Sobczak 505*cdcd52d4SBartosz Sobczak return 0; 506*cdcd52d4SBartosz Sobczak } 507*cdcd52d4SBartosz Sobczak 508*cdcd52d4SBartosz Sobczak /** 509*cdcd52d4SBartosz Sobczak * irdma_sc_qp_create - create qp 510*cdcd52d4SBartosz Sobczak * @qp: sc qp 511*cdcd52d4SBartosz Sobczak * @info: qp create info 512*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 513*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 514*cdcd52d4SBartosz Sobczak */ 515*cdcd52d4SBartosz Sobczak int 516*cdcd52d4SBartosz Sobczak irdma_sc_qp_create(struct irdma_sc_qp *qp, struct irdma_create_qp_info *info, 517*cdcd52d4SBartosz Sobczak u64 scratch, bool post_sq) 518*cdcd52d4SBartosz Sobczak { 519*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 520*cdcd52d4SBartosz Sobczak __le64 *wqe; 521*cdcd52d4SBartosz Sobczak u64 hdr; 522*cdcd52d4SBartosz Sobczak 523*cdcd52d4SBartosz Sobczak cqp = qp->dev->cqp; 524*cdcd52d4SBartosz Sobczak if (qp->qp_uk.qp_id < cqp->dev->hw_attrs.min_hw_qp_id || 525*cdcd52d4SBartosz Sobczak qp->qp_uk.qp_id > (cqp->dev->hmc_info->hmc_obj[IRDMA_HMC_IW_QP].max_cnt - 1)) 526*cdcd52d4SBartosz Sobczak return -EINVAL; 527*cdcd52d4SBartosz Sobczak 528*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 529*cdcd52d4SBartosz Sobczak if (!wqe) 530*cdcd52d4SBartosz Sobczak return -ENOSPC; 531*cdcd52d4SBartosz Sobczak 532*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, qp->hw_host_ctx_pa); 533*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, qp->shadow_area_pa); 534*cdcd52d4SBartosz Sobczak 535*cdcd52d4SBartosz Sobczak hdr = qp->qp_uk.qp_id | 536*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_CREATE_QP, IRDMA_CQPSQ_OPCODE) | 537*cdcd52d4SBartosz Sobczak LS_64((info->ord_valid ? 1 : 0), IRDMA_CQPSQ_QP_ORDVALID) | 538*cdcd52d4SBartosz Sobczak LS_64(info->tcp_ctx_valid, IRDMA_CQPSQ_QP_TOECTXVALID) | 539*cdcd52d4SBartosz Sobczak LS_64(info->mac_valid, IRDMA_CQPSQ_QP_MACVALID) | 540*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.qp_type, IRDMA_CQPSQ_QP_QPTYPE) | 541*cdcd52d4SBartosz Sobczak LS_64(qp->virtual_map, IRDMA_CQPSQ_QP_VQ) | 542*cdcd52d4SBartosz Sobczak LS_64(info->force_lpb, IRDMA_CQPSQ_QP_FORCELOOPBACK) | 543*cdcd52d4SBartosz Sobczak LS_64(info->cq_num_valid, IRDMA_CQPSQ_QP_CQNUMVALID) | 544*cdcd52d4SBartosz Sobczak LS_64(info->arp_cache_idx_valid, IRDMA_CQPSQ_QP_ARPTABIDXVALID) | 545*cdcd52d4SBartosz Sobczak LS_64(info->next_iwarp_state, IRDMA_CQPSQ_QP_NEXTIWSTATE) | 546*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 547*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 548*cdcd52d4SBartosz Sobczak 549*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 550*cdcd52d4SBartosz Sobczak 551*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "QP_CREATE WQE", wqe, 552*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 553*cdcd52d4SBartosz Sobczak if (post_sq) 554*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 555*cdcd52d4SBartosz Sobczak 556*cdcd52d4SBartosz Sobczak return 0; 557*cdcd52d4SBartosz Sobczak } 558*cdcd52d4SBartosz Sobczak 559*cdcd52d4SBartosz Sobczak /** 560*cdcd52d4SBartosz Sobczak * irdma_sc_qp_modify - modify qp cqp wqe 561*cdcd52d4SBartosz Sobczak * @qp: sc qp 562*cdcd52d4SBartosz Sobczak * @info: modify qp info 563*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 564*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 565*cdcd52d4SBartosz Sobczak */ 566*cdcd52d4SBartosz Sobczak int 567*cdcd52d4SBartosz Sobczak irdma_sc_qp_modify(struct irdma_sc_qp *qp, struct irdma_modify_qp_info *info, 568*cdcd52d4SBartosz Sobczak u64 scratch, bool post_sq) 569*cdcd52d4SBartosz Sobczak { 570*cdcd52d4SBartosz Sobczak __le64 *wqe; 571*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 572*cdcd52d4SBartosz Sobczak u64 hdr; 573*cdcd52d4SBartosz Sobczak u8 term_actions = 0; 574*cdcd52d4SBartosz Sobczak u8 term_len = 0; 575*cdcd52d4SBartosz Sobczak 576*cdcd52d4SBartosz Sobczak cqp = qp->dev->cqp; 577*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 578*cdcd52d4SBartosz Sobczak if (!wqe) 579*cdcd52d4SBartosz Sobczak return -ENOSPC; 580*cdcd52d4SBartosz Sobczak 581*cdcd52d4SBartosz Sobczak if (info->next_iwarp_state == IRDMA_QP_STATE_TERMINATE) { 582*cdcd52d4SBartosz Sobczak if (info->dont_send_fin) 583*cdcd52d4SBartosz Sobczak term_actions += IRDMAQP_TERM_SEND_TERM_ONLY; 584*cdcd52d4SBartosz Sobczak if (info->dont_send_term) 585*cdcd52d4SBartosz Sobczak term_actions += IRDMAQP_TERM_SEND_FIN_ONLY; 586*cdcd52d4SBartosz Sobczak if (term_actions == IRDMAQP_TERM_SEND_TERM_AND_FIN || 587*cdcd52d4SBartosz Sobczak term_actions == IRDMAQP_TERM_SEND_TERM_ONLY) 588*cdcd52d4SBartosz Sobczak term_len = info->termlen; 589*cdcd52d4SBartosz Sobczak } 590*cdcd52d4SBartosz Sobczak 591*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 592*cdcd52d4SBartosz Sobczak LS_64(info->new_mss, IRDMA_CQPSQ_QP_NEWMSS) | 593*cdcd52d4SBartosz Sobczak LS_64(term_len, IRDMA_CQPSQ_QP_TERMLEN)); 594*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, qp->hw_host_ctx_pa); 595*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, qp->shadow_area_pa); 596*cdcd52d4SBartosz Sobczak 597*cdcd52d4SBartosz Sobczak hdr = qp->qp_uk.qp_id | 598*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_MODIFY_QP, IRDMA_CQPSQ_OPCODE) | 599*cdcd52d4SBartosz Sobczak LS_64(info->ord_valid, IRDMA_CQPSQ_QP_ORDVALID) | 600*cdcd52d4SBartosz Sobczak LS_64(info->tcp_ctx_valid, IRDMA_CQPSQ_QP_TOECTXVALID) | 601*cdcd52d4SBartosz Sobczak LS_64(info->cached_var_valid, IRDMA_CQPSQ_QP_CACHEDVARVALID) | 602*cdcd52d4SBartosz Sobczak LS_64(qp->virtual_map, IRDMA_CQPSQ_QP_VQ) | 603*cdcd52d4SBartosz Sobczak LS_64(info->force_lpb, IRDMA_CQPSQ_QP_FORCELOOPBACK) | 604*cdcd52d4SBartosz Sobczak LS_64(info->cq_num_valid, IRDMA_CQPSQ_QP_CQNUMVALID) | 605*cdcd52d4SBartosz Sobczak LS_64(info->mac_valid, IRDMA_CQPSQ_QP_MACVALID) | 606*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.qp_type, IRDMA_CQPSQ_QP_QPTYPE) | 607*cdcd52d4SBartosz Sobczak LS_64(info->mss_change, IRDMA_CQPSQ_QP_MSSCHANGE) | 608*cdcd52d4SBartosz Sobczak LS_64(info->remove_hash_idx, IRDMA_CQPSQ_QP_REMOVEHASHENTRY) | 609*cdcd52d4SBartosz Sobczak LS_64(term_actions, IRDMA_CQPSQ_QP_TERMACT) | 610*cdcd52d4SBartosz Sobczak LS_64(info->reset_tcp_conn, IRDMA_CQPSQ_QP_RESETCON) | 611*cdcd52d4SBartosz Sobczak LS_64(info->arp_cache_idx_valid, IRDMA_CQPSQ_QP_ARPTABIDXVALID) | 612*cdcd52d4SBartosz Sobczak LS_64(info->next_iwarp_state, IRDMA_CQPSQ_QP_NEXTIWSTATE) | 613*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 614*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 615*cdcd52d4SBartosz Sobczak 616*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 617*cdcd52d4SBartosz Sobczak 618*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "QP_MODIFY WQE", wqe, 619*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 620*cdcd52d4SBartosz Sobczak if (post_sq) 621*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 622*cdcd52d4SBartosz Sobczak 623*cdcd52d4SBartosz Sobczak return 0; 624*cdcd52d4SBartosz Sobczak } 625*cdcd52d4SBartosz Sobczak 626*cdcd52d4SBartosz Sobczak /** 627*cdcd52d4SBartosz Sobczak * irdma_sc_qp_destroy - cqp destroy qp 628*cdcd52d4SBartosz Sobczak * @qp: sc qp 629*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 630*cdcd52d4SBartosz Sobczak * @remove_hash_idx: flag if to remove hash idx 631*cdcd52d4SBartosz Sobczak * @ignore_mw_bnd: memory window bind flag 632*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 633*cdcd52d4SBartosz Sobczak */ 634*cdcd52d4SBartosz Sobczak int 635*cdcd52d4SBartosz Sobczak irdma_sc_qp_destroy(struct irdma_sc_qp *qp, u64 scratch, 636*cdcd52d4SBartosz Sobczak bool remove_hash_idx, bool ignore_mw_bnd, bool post_sq) 637*cdcd52d4SBartosz Sobczak { 638*cdcd52d4SBartosz Sobczak __le64 *wqe; 639*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 640*cdcd52d4SBartosz Sobczak u64 hdr; 641*cdcd52d4SBartosz Sobczak 642*cdcd52d4SBartosz Sobczak cqp = qp->dev->cqp; 643*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 644*cdcd52d4SBartosz Sobczak if (!wqe) 645*cdcd52d4SBartosz Sobczak return -ENOSPC; 646*cdcd52d4SBartosz Sobczak 647*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, qp->hw_host_ctx_pa); 648*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, qp->shadow_area_pa); 649*cdcd52d4SBartosz Sobczak 650*cdcd52d4SBartosz Sobczak hdr = qp->qp_uk.qp_id | 651*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_DESTROY_QP, IRDMA_CQPSQ_OPCODE) | 652*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.qp_type, IRDMA_CQPSQ_QP_QPTYPE) | 653*cdcd52d4SBartosz Sobczak LS_64(ignore_mw_bnd, IRDMA_CQPSQ_QP_IGNOREMWBOUND) | 654*cdcd52d4SBartosz Sobczak LS_64(remove_hash_idx, IRDMA_CQPSQ_QP_REMOVEHASHENTRY) | 655*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 656*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 657*cdcd52d4SBartosz Sobczak 658*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 659*cdcd52d4SBartosz Sobczak 660*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "QP_DESTROY WQE", wqe, 661*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 662*cdcd52d4SBartosz Sobczak if (post_sq) 663*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 664*cdcd52d4SBartosz Sobczak 665*cdcd52d4SBartosz Sobczak return 0; 666*cdcd52d4SBartosz Sobczak } 667*cdcd52d4SBartosz Sobczak 668*cdcd52d4SBartosz Sobczak /** 669*cdcd52d4SBartosz Sobczak * irdma_sc_get_encoded_ird_size - 670*cdcd52d4SBartosz Sobczak * @ird_size: IRD size 671*cdcd52d4SBartosz Sobczak * The ird from the connection is rounded to a supported HW setting and then encoded 672*cdcd52d4SBartosz Sobczak * for ird_size field of qp_ctx. Consumers are expected to provide valid ird size based 673*cdcd52d4SBartosz Sobczak * on hardware attributes. IRD size defaults to a value of 4 in case of invalid input 674*cdcd52d4SBartosz Sobczak */ 675*cdcd52d4SBartosz Sobczak static u8 irdma_sc_get_encoded_ird_size(u16 ird_size) { 676*cdcd52d4SBartosz Sobczak switch (ird_size ? 677*cdcd52d4SBartosz Sobczak roundup_pow_of_two(2 * ird_size) : 4) { 678*cdcd52d4SBartosz Sobczak case 256: 679*cdcd52d4SBartosz Sobczak return IRDMA_IRD_HW_SIZE_256; 680*cdcd52d4SBartosz Sobczak case 128: 681*cdcd52d4SBartosz Sobczak return IRDMA_IRD_HW_SIZE_128; 682*cdcd52d4SBartosz Sobczak case 64: 683*cdcd52d4SBartosz Sobczak case 32: 684*cdcd52d4SBartosz Sobczak return IRDMA_IRD_HW_SIZE_64; 685*cdcd52d4SBartosz Sobczak case 16: 686*cdcd52d4SBartosz Sobczak case 8: 687*cdcd52d4SBartosz Sobczak return IRDMA_IRD_HW_SIZE_16; 688*cdcd52d4SBartosz Sobczak case 4: 689*cdcd52d4SBartosz Sobczak default: 690*cdcd52d4SBartosz Sobczak break; 691*cdcd52d4SBartosz Sobczak } 692*cdcd52d4SBartosz Sobczak 693*cdcd52d4SBartosz Sobczak return IRDMA_IRD_HW_SIZE_4; 694*cdcd52d4SBartosz Sobczak } 695*cdcd52d4SBartosz Sobczak 696*cdcd52d4SBartosz Sobczak /** 697*cdcd52d4SBartosz Sobczak * irdma_sc_qp_setctx_roce - set qp's context 698*cdcd52d4SBartosz Sobczak * @qp: sc qp 699*cdcd52d4SBartosz Sobczak * @qp_ctx: context ptr 700*cdcd52d4SBartosz Sobczak * @info: ctx info 701*cdcd52d4SBartosz Sobczak */ 702*cdcd52d4SBartosz Sobczak void 703*cdcd52d4SBartosz Sobczak irdma_sc_qp_setctx_roce(struct irdma_sc_qp *qp, __le64 * qp_ctx, 704*cdcd52d4SBartosz Sobczak struct irdma_qp_host_ctx_info *info) 705*cdcd52d4SBartosz Sobczak { 706*cdcd52d4SBartosz Sobczak struct irdma_roce_offload_info *roce_info; 707*cdcd52d4SBartosz Sobczak struct irdma_udp_offload_info *udp; 708*cdcd52d4SBartosz Sobczak u8 push_mode_en; 709*cdcd52d4SBartosz Sobczak u32 push_idx; 710*cdcd52d4SBartosz Sobczak u64 mac; 711*cdcd52d4SBartosz Sobczak 712*cdcd52d4SBartosz Sobczak roce_info = info->roce_info; 713*cdcd52d4SBartosz Sobczak udp = info->udp_info; 714*cdcd52d4SBartosz Sobczak 715*cdcd52d4SBartosz Sobczak mac = LS_64_1(roce_info->mac_addr[5], 16) | 716*cdcd52d4SBartosz Sobczak LS_64_1(roce_info->mac_addr[4], 24) | 717*cdcd52d4SBartosz Sobczak LS_64_1(roce_info->mac_addr[3], 32) | 718*cdcd52d4SBartosz Sobczak LS_64_1(roce_info->mac_addr[2], 40) | 719*cdcd52d4SBartosz Sobczak LS_64_1(roce_info->mac_addr[1], 48) | 720*cdcd52d4SBartosz Sobczak LS_64_1(roce_info->mac_addr[0], 56); 721*cdcd52d4SBartosz Sobczak 722*cdcd52d4SBartosz Sobczak qp->user_pri = info->user_pri; 723*cdcd52d4SBartosz Sobczak if (qp->push_idx == IRDMA_INVALID_PUSH_PAGE_INDEX) { 724*cdcd52d4SBartosz Sobczak push_mode_en = 0; 725*cdcd52d4SBartosz Sobczak push_idx = 0; 726*cdcd52d4SBartosz Sobczak } else { 727*cdcd52d4SBartosz Sobczak push_mode_en = 1; 728*cdcd52d4SBartosz Sobczak push_idx = qp->push_idx; 729*cdcd52d4SBartosz Sobczak } 730*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_0, 731*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.rq_wqe_size, IRDMAQPC_RQWQESIZE) | 732*cdcd52d4SBartosz Sobczak LS_64(qp->rcv_tph_en, IRDMAQPC_RCVTPHEN) | 733*cdcd52d4SBartosz Sobczak LS_64(qp->xmit_tph_en, IRDMAQPC_XMITTPHEN) | 734*cdcd52d4SBartosz Sobczak LS_64(qp->rq_tph_en, IRDMAQPC_RQTPHEN) | 735*cdcd52d4SBartosz Sobczak LS_64(qp->sq_tph_en, IRDMAQPC_SQTPHEN) | 736*cdcd52d4SBartosz Sobczak LS_64(push_idx, IRDMAQPC_PPIDX) | 737*cdcd52d4SBartosz Sobczak LS_64(push_mode_en, IRDMAQPC_PMENA) | 738*cdcd52d4SBartosz Sobczak LS_64(roce_info->pd_id >> 16, IRDMAQPC_PDIDXHI) | 739*cdcd52d4SBartosz Sobczak LS_64(roce_info->dctcp_en, IRDMAQPC_DC_TCP_EN) | 740*cdcd52d4SBartosz Sobczak LS_64(roce_info->err_rq_idx_valid, IRDMAQPC_ERR_RQ_IDX_VALID) | 741*cdcd52d4SBartosz Sobczak LS_64(roce_info->is_qp1, IRDMAQPC_ISQP1) | 742*cdcd52d4SBartosz Sobczak LS_64(roce_info->roce_tver, IRDMAQPC_ROCE_TVER) | 743*cdcd52d4SBartosz Sobczak LS_64(udp->ipv4, IRDMAQPC_IPV4) | 744*cdcd52d4SBartosz Sobczak LS_64(udp->insert_vlan_tag, IRDMAQPC_INSERTVLANTAG)); 745*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_8, qp->sq_pa); 746*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_16, qp->rq_pa); 747*cdcd52d4SBartosz Sobczak if (roce_info->dcqcn_en || roce_info->dctcp_en) { 748*cdcd52d4SBartosz Sobczak udp->tos &= ~ECN_CODE_PT_MASK; 749*cdcd52d4SBartosz Sobczak udp->tos |= ECN_CODE_PT_VAL; 750*cdcd52d4SBartosz Sobczak } 751*cdcd52d4SBartosz Sobczak 752*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_24, 753*cdcd52d4SBartosz Sobczak LS_64(qp->hw_rq_size, IRDMAQPC_RQSIZE) | 754*cdcd52d4SBartosz Sobczak LS_64(qp->hw_sq_size, IRDMAQPC_SQSIZE) | 755*cdcd52d4SBartosz Sobczak LS_64(udp->ttl, IRDMAQPC_TTL) | LS_64(udp->tos, IRDMAQPC_TOS) | 756*cdcd52d4SBartosz Sobczak LS_64(udp->src_port, IRDMAQPC_SRCPORTNUM) | 757*cdcd52d4SBartosz Sobczak LS_64(udp->dst_port, IRDMAQPC_DESTPORTNUM)); 758*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_32, 759*cdcd52d4SBartosz Sobczak LS_64(udp->dest_ip_addr[2], IRDMAQPC_DESTIPADDR2) | 760*cdcd52d4SBartosz Sobczak LS_64(udp->dest_ip_addr[3], IRDMAQPC_DESTIPADDR3)); 761*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_40, 762*cdcd52d4SBartosz Sobczak LS_64(udp->dest_ip_addr[0], IRDMAQPC_DESTIPADDR0) | 763*cdcd52d4SBartosz Sobczak LS_64(udp->dest_ip_addr[1], IRDMAQPC_DESTIPADDR1)); 764*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_48, 765*cdcd52d4SBartosz Sobczak LS_64(udp->snd_mss, IRDMAQPC_SNDMSS) | 766*cdcd52d4SBartosz Sobczak LS_64(udp->vlan_tag, IRDMAQPC_VLANTAG) | 767*cdcd52d4SBartosz Sobczak LS_64(udp->arp_idx, IRDMAQPC_ARPIDX)); 768*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_56, 769*cdcd52d4SBartosz Sobczak LS_64(roce_info->p_key, IRDMAQPC_PKEY) | 770*cdcd52d4SBartosz Sobczak LS_64(roce_info->pd_id, IRDMAQPC_PDIDX) | 771*cdcd52d4SBartosz Sobczak LS_64(roce_info->ack_credits, IRDMAQPC_ACKCREDITS) | 772*cdcd52d4SBartosz Sobczak LS_64(udp->flow_label, IRDMAQPC_FLOWLABEL)); 773*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_64, 774*cdcd52d4SBartosz Sobczak LS_64(roce_info->qkey, IRDMAQPC_QKEY) | 775*cdcd52d4SBartosz Sobczak LS_64(roce_info->dest_qp, IRDMAQPC_DESTQP)); 776*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_80, 777*cdcd52d4SBartosz Sobczak LS_64(udp->psn_nxt, IRDMAQPC_PSNNXT) | 778*cdcd52d4SBartosz Sobczak LS_64(udp->lsn, IRDMAQPC_LSN)); 779*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_88, LS_64(udp->epsn, IRDMAQPC_EPSN)); 780*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_96, 781*cdcd52d4SBartosz Sobczak LS_64(udp->psn_max, IRDMAQPC_PSNMAX) | 782*cdcd52d4SBartosz Sobczak LS_64(udp->psn_una, IRDMAQPC_PSNUNA)); 783*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_112, 784*cdcd52d4SBartosz Sobczak LS_64(udp->cwnd, IRDMAQPC_CWNDROCE)); 785*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_128, 786*cdcd52d4SBartosz Sobczak LS_64(roce_info->err_rq_idx, IRDMAQPC_ERR_RQ_IDX) | 787*cdcd52d4SBartosz Sobczak LS_64(udp->rnr_nak_thresh, IRDMAQPC_RNRNAK_THRESH) | 788*cdcd52d4SBartosz Sobczak LS_64(udp->rexmit_thresh, IRDMAQPC_REXMIT_THRESH) | 789*cdcd52d4SBartosz Sobczak LS_64(roce_info->rtomin, IRDMAQPC_RTOMIN)); 790*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_136, 791*cdcd52d4SBartosz Sobczak LS_64(info->send_cq_num, IRDMAQPC_TXCQNUM) | 792*cdcd52d4SBartosz Sobczak LS_64(info->rcv_cq_num, IRDMAQPC_RXCQNUM)); 793*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_144, 794*cdcd52d4SBartosz Sobczak LS_64(info->stats_idx, IRDMAQPC_STAT_INDEX)); 795*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_152, mac); 796*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_160, 797*cdcd52d4SBartosz Sobczak LS_64(roce_info->ord_size, IRDMAQPC_ORDSIZE) | 798*cdcd52d4SBartosz Sobczak LS_64(irdma_sc_get_encoded_ird_size(roce_info->ird_size), IRDMAQPC_IRDSIZE) | 799*cdcd52d4SBartosz Sobczak LS_64(roce_info->wr_rdresp_en, IRDMAQPC_WRRDRSPOK) | 800*cdcd52d4SBartosz Sobczak LS_64(roce_info->rd_en, IRDMAQPC_RDOK) | 801*cdcd52d4SBartosz Sobczak LS_64(info->stats_idx_valid, IRDMAQPC_USESTATSINSTANCE) | 802*cdcd52d4SBartosz Sobczak LS_64(roce_info->bind_en, IRDMAQPC_BINDEN) | 803*cdcd52d4SBartosz Sobczak LS_64(roce_info->fast_reg_en, IRDMAQPC_FASTREGEN) | 804*cdcd52d4SBartosz Sobczak LS_64(roce_info->dcqcn_en, IRDMAQPC_DCQCNENABLE) | 805*cdcd52d4SBartosz Sobczak LS_64(roce_info->rcv_no_icrc, IRDMAQPC_RCVNOICRC) | 806*cdcd52d4SBartosz Sobczak LS_64(roce_info->fw_cc_enable, IRDMAQPC_FW_CC_ENABLE) | 807*cdcd52d4SBartosz Sobczak LS_64(roce_info->udprivcq_en, IRDMAQPC_UDPRIVCQENABLE) | 808*cdcd52d4SBartosz Sobczak LS_64(roce_info->priv_mode_en, IRDMAQPC_PRIVEN) | 809*cdcd52d4SBartosz Sobczak LS_64(roce_info->timely_en, IRDMAQPC_TIMELYENABLE)); 810*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_168, 811*cdcd52d4SBartosz Sobczak LS_64(info->qp_compl_ctx, IRDMAQPC_QPCOMPCTX)); 812*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_176, 813*cdcd52d4SBartosz Sobczak LS_64(qp->sq_tph_val, IRDMAQPC_SQTPHVAL) | 814*cdcd52d4SBartosz Sobczak LS_64(qp->rq_tph_val, IRDMAQPC_RQTPHVAL) | 815*cdcd52d4SBartosz Sobczak LS_64(qp->qs_handle, IRDMAQPC_QSHANDLE)); 816*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_184, 817*cdcd52d4SBartosz Sobczak LS_64(udp->local_ipaddr[3], IRDMAQPC_LOCAL_IPADDR3) | 818*cdcd52d4SBartosz Sobczak LS_64(udp->local_ipaddr[2], IRDMAQPC_LOCAL_IPADDR2)); 819*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_192, 820*cdcd52d4SBartosz Sobczak LS_64(udp->local_ipaddr[1], IRDMAQPC_LOCAL_IPADDR1) | 821*cdcd52d4SBartosz Sobczak LS_64(udp->local_ipaddr[0], IRDMAQPC_LOCAL_IPADDR0)); 822*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_200, 823*cdcd52d4SBartosz Sobczak LS_64(roce_info->t_high, IRDMAQPC_THIGH) | 824*cdcd52d4SBartosz Sobczak LS_64(roce_info->t_low, IRDMAQPC_TLOW)); 825*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_208, 826*cdcd52d4SBartosz Sobczak LS_64(info->rem_endpoint_idx, IRDMAQPC_REMENDPOINTIDX)); 827*cdcd52d4SBartosz Sobczak 828*cdcd52d4SBartosz Sobczak irdma_debug_buf(qp->dev, IRDMA_DEBUG_WQE, "QP_HOST CTX WQE", qp_ctx, 829*cdcd52d4SBartosz Sobczak IRDMA_QP_CTX_SIZE); 830*cdcd52d4SBartosz Sobczak } 831*cdcd52d4SBartosz Sobczak 832*cdcd52d4SBartosz Sobczak /* 833*cdcd52d4SBartosz Sobczak * irdma_sc_alloc_local_mac_entry - allocate a mac entry @cqp: struct for cqp hw @scratch: u64 saved to be used during 834*cdcd52d4SBartosz Sobczak * cqp completion @post_sq: flag for cqp db to ring 835*cdcd52d4SBartosz Sobczak */ 836*cdcd52d4SBartosz Sobczak static int 837*cdcd52d4SBartosz Sobczak irdma_sc_alloc_local_mac_entry(struct irdma_sc_cqp *cqp, u64 scratch, 838*cdcd52d4SBartosz Sobczak bool post_sq) 839*cdcd52d4SBartosz Sobczak { 840*cdcd52d4SBartosz Sobczak __le64 *wqe; 841*cdcd52d4SBartosz Sobczak u64 hdr; 842*cdcd52d4SBartosz Sobczak 843*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 844*cdcd52d4SBartosz Sobczak if (!wqe) 845*cdcd52d4SBartosz Sobczak return -ENOSPC; 846*cdcd52d4SBartosz Sobczak 847*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMA_CQP_OP_ALLOCATE_LOC_MAC_TABLE_ENTRY, 848*cdcd52d4SBartosz Sobczak IRDMA_CQPSQ_OPCODE) | 849*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 850*cdcd52d4SBartosz Sobczak 851*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 852*cdcd52d4SBartosz Sobczak 853*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 854*cdcd52d4SBartosz Sobczak 855*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "ALLOCATE_LOCAL_MAC WQE", 856*cdcd52d4SBartosz Sobczak wqe, IRDMA_CQP_WQE_SIZE * 8); 857*cdcd52d4SBartosz Sobczak 858*cdcd52d4SBartosz Sobczak if (post_sq) 859*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 860*cdcd52d4SBartosz Sobczak return 0; 861*cdcd52d4SBartosz Sobczak } 862*cdcd52d4SBartosz Sobczak 863*cdcd52d4SBartosz Sobczak /** 864*cdcd52d4SBartosz Sobczak * irdma_sc_add_local_mac_entry - add mac enry 865*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 866*cdcd52d4SBartosz Sobczak * @info:mac addr info 867*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 868*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 869*cdcd52d4SBartosz Sobczak */ 870*cdcd52d4SBartosz Sobczak static int 871*cdcd52d4SBartosz Sobczak irdma_sc_add_local_mac_entry(struct irdma_sc_cqp *cqp, 872*cdcd52d4SBartosz Sobczak struct irdma_local_mac_entry_info *info, 873*cdcd52d4SBartosz Sobczak u64 scratch, bool post_sq) 874*cdcd52d4SBartosz Sobczak { 875*cdcd52d4SBartosz Sobczak __le64 *wqe; 876*cdcd52d4SBartosz Sobczak u64 temp, header; 877*cdcd52d4SBartosz Sobczak 878*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 879*cdcd52d4SBartosz Sobczak if (!wqe) 880*cdcd52d4SBartosz Sobczak return -ENOSPC; 881*cdcd52d4SBartosz Sobczak temp = info->mac_addr[5] | LS_64_1(info->mac_addr[4], 8) | 882*cdcd52d4SBartosz Sobczak LS_64_1(info->mac_addr[3], 16) | LS_64_1(info->mac_addr[2], 24) | 883*cdcd52d4SBartosz Sobczak LS_64_1(info->mac_addr[1], 32) | LS_64_1(info->mac_addr[0], 40); 884*cdcd52d4SBartosz Sobczak 885*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, temp); 886*cdcd52d4SBartosz Sobczak 887*cdcd52d4SBartosz Sobczak header = LS_64(info->entry_idx, IRDMA_CQPSQ_MLM_TABLEIDX) | 888*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_MANAGE_LOC_MAC_TABLE, IRDMA_CQPSQ_OPCODE) | 889*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 890*cdcd52d4SBartosz Sobczak 891*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 892*cdcd52d4SBartosz Sobczak 893*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, header); 894*cdcd52d4SBartosz Sobczak 895*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "ADD_LOCAL_MAC WQE", wqe, 896*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 897*cdcd52d4SBartosz Sobczak 898*cdcd52d4SBartosz Sobczak if (post_sq) 899*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 900*cdcd52d4SBartosz Sobczak return 0; 901*cdcd52d4SBartosz Sobczak } 902*cdcd52d4SBartosz Sobczak 903*cdcd52d4SBartosz Sobczak /** 904*cdcd52d4SBartosz Sobczak * irdma_sc_del_local_mac_entry - cqp wqe to dele local mac 905*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 906*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 907*cdcd52d4SBartosz Sobczak * @entry_idx: index of mac entry 908*cdcd52d4SBartosz Sobczak * @ignore_ref_count: to force mac adde delete 909*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 910*cdcd52d4SBartosz Sobczak */ 911*cdcd52d4SBartosz Sobczak static int 912*cdcd52d4SBartosz Sobczak irdma_sc_del_local_mac_entry(struct irdma_sc_cqp *cqp, u64 scratch, 913*cdcd52d4SBartosz Sobczak u16 entry_idx, u8 ignore_ref_count, 914*cdcd52d4SBartosz Sobczak bool post_sq) 915*cdcd52d4SBartosz Sobczak { 916*cdcd52d4SBartosz Sobczak __le64 *wqe; 917*cdcd52d4SBartosz Sobczak u64 header; 918*cdcd52d4SBartosz Sobczak 919*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 920*cdcd52d4SBartosz Sobczak if (!wqe) 921*cdcd52d4SBartosz Sobczak return -ENOSPC; 922*cdcd52d4SBartosz Sobczak header = LS_64(entry_idx, IRDMA_CQPSQ_MLM_TABLEIDX) | 923*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_MANAGE_LOC_MAC_TABLE, IRDMA_CQPSQ_OPCODE) | 924*cdcd52d4SBartosz Sobczak LS_64(1, IRDMA_CQPSQ_MLM_FREEENTRY) | 925*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID) | 926*cdcd52d4SBartosz Sobczak LS_64(ignore_ref_count, IRDMA_CQPSQ_MLM_IGNORE_REF_CNT); 927*cdcd52d4SBartosz Sobczak 928*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 929*cdcd52d4SBartosz Sobczak 930*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, header); 931*cdcd52d4SBartosz Sobczak 932*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "DEL_LOCAL_MAC_IPADDR WQE", 933*cdcd52d4SBartosz Sobczak wqe, IRDMA_CQP_WQE_SIZE * 8); 934*cdcd52d4SBartosz Sobczak 935*cdcd52d4SBartosz Sobczak if (post_sq) 936*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 937*cdcd52d4SBartosz Sobczak return 0; 938*cdcd52d4SBartosz Sobczak } 939*cdcd52d4SBartosz Sobczak 940*cdcd52d4SBartosz Sobczak /** 941*cdcd52d4SBartosz Sobczak * irdma_sc_qp_setctx - set qp's context 942*cdcd52d4SBartosz Sobczak * @qp: sc qp 943*cdcd52d4SBartosz Sobczak * @qp_ctx: context ptr 944*cdcd52d4SBartosz Sobczak * @info: ctx info 945*cdcd52d4SBartosz Sobczak */ 946*cdcd52d4SBartosz Sobczak void 947*cdcd52d4SBartosz Sobczak irdma_sc_qp_setctx(struct irdma_sc_qp *qp, __le64 * qp_ctx, 948*cdcd52d4SBartosz Sobczak struct irdma_qp_host_ctx_info *info) 949*cdcd52d4SBartosz Sobczak { 950*cdcd52d4SBartosz Sobczak struct irdma_iwarp_offload_info *iw; 951*cdcd52d4SBartosz Sobczak struct irdma_tcp_offload_info *tcp; 952*cdcd52d4SBartosz Sobczak struct irdma_sc_dev *dev; 953*cdcd52d4SBartosz Sobczak u8 push_mode_en; 954*cdcd52d4SBartosz Sobczak u32 push_idx; 955*cdcd52d4SBartosz Sobczak u64 qw0, qw3, qw7 = 0, qw16 = 0; 956*cdcd52d4SBartosz Sobczak u64 mac = 0; 957*cdcd52d4SBartosz Sobczak 958*cdcd52d4SBartosz Sobczak iw = info->iwarp_info; 959*cdcd52d4SBartosz Sobczak tcp = info->tcp_info; 960*cdcd52d4SBartosz Sobczak dev = qp->dev; 961*cdcd52d4SBartosz Sobczak if (iw->rcv_mark_en) { 962*cdcd52d4SBartosz Sobczak qp->pfpdu.marker_len = 4; 963*cdcd52d4SBartosz Sobczak qp->pfpdu.rcv_start_seq = tcp->rcv_nxt; 964*cdcd52d4SBartosz Sobczak } 965*cdcd52d4SBartosz Sobczak qp->user_pri = info->user_pri; 966*cdcd52d4SBartosz Sobczak if (qp->push_idx == IRDMA_INVALID_PUSH_PAGE_INDEX) { 967*cdcd52d4SBartosz Sobczak push_mode_en = 0; 968*cdcd52d4SBartosz Sobczak push_idx = 0; 969*cdcd52d4SBartosz Sobczak } else { 970*cdcd52d4SBartosz Sobczak push_mode_en = 1; 971*cdcd52d4SBartosz Sobczak push_idx = qp->push_idx; 972*cdcd52d4SBartosz Sobczak } 973*cdcd52d4SBartosz Sobczak qw0 = LS_64(qp->qp_uk.rq_wqe_size, IRDMAQPC_RQWQESIZE) | 974*cdcd52d4SBartosz Sobczak LS_64(qp->rcv_tph_en, IRDMAQPC_RCVTPHEN) | 975*cdcd52d4SBartosz Sobczak LS_64(qp->xmit_tph_en, IRDMAQPC_XMITTPHEN) | 976*cdcd52d4SBartosz Sobczak LS_64(qp->rq_tph_en, IRDMAQPC_RQTPHEN) | 977*cdcd52d4SBartosz Sobczak LS_64(qp->sq_tph_en, IRDMAQPC_SQTPHEN) | 978*cdcd52d4SBartosz Sobczak LS_64(push_idx, IRDMAQPC_PPIDX) | 979*cdcd52d4SBartosz Sobczak LS_64(push_mode_en, IRDMAQPC_PMENA); 980*cdcd52d4SBartosz Sobczak 981*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_8, qp->sq_pa); 982*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_16, qp->rq_pa); 983*cdcd52d4SBartosz Sobczak 984*cdcd52d4SBartosz Sobczak qw3 = LS_64(qp->hw_rq_size, IRDMAQPC_RQSIZE) | 985*cdcd52d4SBartosz Sobczak LS_64(qp->hw_sq_size, IRDMAQPC_SQSIZE); 986*cdcd52d4SBartosz Sobczak if (dev->hw_attrs.uk_attrs.hw_rev == IRDMA_GEN_1) 987*cdcd52d4SBartosz Sobczak qw3 |= LS_64(qp->src_mac_addr_idx, IRDMAQPC_GEN1_SRCMACADDRIDX); 988*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_136, 989*cdcd52d4SBartosz Sobczak LS_64(info->send_cq_num, IRDMAQPC_TXCQNUM) | 990*cdcd52d4SBartosz Sobczak LS_64(info->rcv_cq_num, IRDMAQPC_RXCQNUM)); 991*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_168, 992*cdcd52d4SBartosz Sobczak LS_64(info->qp_compl_ctx, IRDMAQPC_QPCOMPCTX)); 993*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_176, 994*cdcd52d4SBartosz Sobczak LS_64(qp->sq_tph_val, IRDMAQPC_SQTPHVAL) | 995*cdcd52d4SBartosz Sobczak LS_64(qp->rq_tph_val, IRDMAQPC_RQTPHVAL) | 996*cdcd52d4SBartosz Sobczak LS_64(qp->qs_handle, IRDMAQPC_QSHANDLE) | 997*cdcd52d4SBartosz Sobczak LS_64(qp->ieq_qp, IRDMAQPC_EXCEPTION_LAN_QUEUE)); 998*cdcd52d4SBartosz Sobczak if (info->iwarp_info_valid) { 999*cdcd52d4SBartosz Sobczak qw0 |= LS_64(iw->ddp_ver, IRDMAQPC_DDP_VER) | 1000*cdcd52d4SBartosz Sobczak LS_64(iw->rdmap_ver, IRDMAQPC_RDMAP_VER) | 1001*cdcd52d4SBartosz Sobczak LS_64(iw->dctcp_en, IRDMAQPC_DC_TCP_EN) | 1002*cdcd52d4SBartosz Sobczak LS_64(iw->ecn_en, IRDMAQPC_ECN_EN) | 1003*cdcd52d4SBartosz Sobczak LS_64(iw->ib_rd_en, IRDMAQPC_IBRDENABLE) | 1004*cdcd52d4SBartosz Sobczak LS_64(iw->pd_id >> 16, IRDMAQPC_PDIDXHI) | 1005*cdcd52d4SBartosz Sobczak LS_64(iw->err_rq_idx_valid, IRDMAQPC_ERR_RQ_IDX_VALID); 1006*cdcd52d4SBartosz Sobczak qw7 |= LS_64(iw->pd_id, IRDMAQPC_PDIDX); 1007*cdcd52d4SBartosz Sobczak qw16 |= LS_64(iw->err_rq_idx, IRDMAQPC_ERR_RQ_IDX) | 1008*cdcd52d4SBartosz Sobczak LS_64(iw->rtomin, IRDMAQPC_RTOMIN); 1009*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_144, 1010*cdcd52d4SBartosz Sobczak LS_64(qp->q2_pa >> 8, IRDMAQPC_Q2ADDR) | 1011*cdcd52d4SBartosz Sobczak LS_64(info->stats_idx, IRDMAQPC_STAT_INDEX)); 1012*cdcd52d4SBartosz Sobczak 1013*cdcd52d4SBartosz Sobczak if (dev->hw_attrs.uk_attrs.hw_rev >= IRDMA_GEN_2) { 1014*cdcd52d4SBartosz Sobczak mac = LS_64_1(iw->mac_addr[5], 16) | 1015*cdcd52d4SBartosz Sobczak LS_64_1(iw->mac_addr[4], 24) | 1016*cdcd52d4SBartosz Sobczak LS_64_1(iw->mac_addr[3], 32) | 1017*cdcd52d4SBartosz Sobczak LS_64_1(iw->mac_addr[2], 40) | 1018*cdcd52d4SBartosz Sobczak LS_64_1(iw->mac_addr[1], 48) | 1019*cdcd52d4SBartosz Sobczak LS_64_1(iw->mac_addr[0], 56); 1020*cdcd52d4SBartosz Sobczak } 1021*cdcd52d4SBartosz Sobczak 1022*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_152, 1023*cdcd52d4SBartosz Sobczak mac | LS_64(iw->last_byte_sent, IRDMAQPC_LASTBYTESENT)); 1024*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_160, 1025*cdcd52d4SBartosz Sobczak LS_64(iw->ord_size, IRDMAQPC_ORDSIZE) | 1026*cdcd52d4SBartosz Sobczak LS_64(irdma_sc_get_encoded_ird_size(iw->ird_size), IRDMAQPC_IRDSIZE) | 1027*cdcd52d4SBartosz Sobczak LS_64(iw->wr_rdresp_en, IRDMAQPC_WRRDRSPOK) | 1028*cdcd52d4SBartosz Sobczak LS_64(iw->rd_en, IRDMAQPC_RDOK) | 1029*cdcd52d4SBartosz Sobczak LS_64(iw->snd_mark_en, IRDMAQPC_SNDMARKERS) | 1030*cdcd52d4SBartosz Sobczak LS_64(iw->bind_en, IRDMAQPC_BINDEN) | 1031*cdcd52d4SBartosz Sobczak LS_64(iw->fast_reg_en, IRDMAQPC_FASTREGEN) | 1032*cdcd52d4SBartosz Sobczak LS_64(iw->priv_mode_en, IRDMAQPC_PRIVEN) | 1033*cdcd52d4SBartosz Sobczak LS_64(info->stats_idx_valid, IRDMAQPC_USESTATSINSTANCE) | 1034*cdcd52d4SBartosz Sobczak LS_64(1, IRDMAQPC_IWARPMODE) | 1035*cdcd52d4SBartosz Sobczak LS_64(iw->rcv_mark_en, IRDMAQPC_RCVMARKERS) | 1036*cdcd52d4SBartosz Sobczak LS_64(iw->align_hdrs, IRDMAQPC_ALIGNHDRS) | 1037*cdcd52d4SBartosz Sobczak LS_64(iw->rcv_no_mpa_crc, IRDMAQPC_RCVNOMPACRC) | 1038*cdcd52d4SBartosz Sobczak LS_64(iw->rcv_mark_offset, IRDMAQPC_RCVMARKOFFSET) | 1039*cdcd52d4SBartosz Sobczak LS_64(iw->snd_mark_offset, IRDMAQPC_SNDMARKOFFSET) | 1040*cdcd52d4SBartosz Sobczak LS_64(iw->timely_en, IRDMAQPC_TIMELYENABLE)); 1041*cdcd52d4SBartosz Sobczak } 1042*cdcd52d4SBartosz Sobczak if (info->tcp_info_valid) { 1043*cdcd52d4SBartosz Sobczak qw0 |= LS_64(tcp->ipv4, IRDMAQPC_IPV4) | 1044*cdcd52d4SBartosz Sobczak LS_64(tcp->no_nagle, IRDMAQPC_NONAGLE) | 1045*cdcd52d4SBartosz Sobczak LS_64(tcp->insert_vlan_tag, IRDMAQPC_INSERTVLANTAG) | 1046*cdcd52d4SBartosz Sobczak LS_64(tcp->time_stamp, IRDMAQPC_TIMESTAMP) | 1047*cdcd52d4SBartosz Sobczak LS_64(tcp->cwnd_inc_limit, IRDMAQPC_LIMIT) | 1048*cdcd52d4SBartosz Sobczak LS_64(tcp->drop_ooo_seg, IRDMAQPC_DROPOOOSEG) | 1049*cdcd52d4SBartosz Sobczak LS_64(tcp->dup_ack_thresh, IRDMAQPC_DUPACK_THRESH); 1050*cdcd52d4SBartosz Sobczak 1051*cdcd52d4SBartosz Sobczak if (iw->ecn_en || iw->dctcp_en) { 1052*cdcd52d4SBartosz Sobczak tcp->tos &= ~ECN_CODE_PT_MASK; 1053*cdcd52d4SBartosz Sobczak tcp->tos |= ECN_CODE_PT_VAL; 1054*cdcd52d4SBartosz Sobczak } 1055*cdcd52d4SBartosz Sobczak 1056*cdcd52d4SBartosz Sobczak qw3 |= LS_64(tcp->ttl, IRDMAQPC_TTL) | 1057*cdcd52d4SBartosz Sobczak LS_64(tcp->avoid_stretch_ack, IRDMAQPC_AVOIDSTRETCHACK) | 1058*cdcd52d4SBartosz Sobczak LS_64(tcp->tos, IRDMAQPC_TOS) | 1059*cdcd52d4SBartosz Sobczak LS_64(tcp->src_port, IRDMAQPC_SRCPORTNUM) | 1060*cdcd52d4SBartosz Sobczak LS_64(tcp->dst_port, IRDMAQPC_DESTPORTNUM); 1061*cdcd52d4SBartosz Sobczak if (dev->hw_attrs.uk_attrs.hw_rev == IRDMA_GEN_1) { 1062*cdcd52d4SBartosz Sobczak qw3 |= LS_64(tcp->src_mac_addr_idx, 1063*cdcd52d4SBartosz Sobczak IRDMAQPC_GEN1_SRCMACADDRIDX); 1064*cdcd52d4SBartosz Sobczak 1065*cdcd52d4SBartosz Sobczak qp->src_mac_addr_idx = tcp->src_mac_addr_idx; 1066*cdcd52d4SBartosz Sobczak } 1067*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_32, 1068*cdcd52d4SBartosz Sobczak LS_64(tcp->dest_ip_addr[2], IRDMAQPC_DESTIPADDR2) | 1069*cdcd52d4SBartosz Sobczak LS_64(tcp->dest_ip_addr[3], IRDMAQPC_DESTIPADDR3)); 1070*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_40, 1071*cdcd52d4SBartosz Sobczak LS_64(tcp->dest_ip_addr[0], IRDMAQPC_DESTIPADDR0) | 1072*cdcd52d4SBartosz Sobczak LS_64(tcp->dest_ip_addr[1], IRDMAQPC_DESTIPADDR1)); 1073*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_48, 1074*cdcd52d4SBartosz Sobczak LS_64(tcp->snd_mss, IRDMAQPC_SNDMSS) | 1075*cdcd52d4SBartosz Sobczak LS_64(tcp->syn_rst_handling, IRDMAQPC_SYN_RST_HANDLING) | 1076*cdcd52d4SBartosz Sobczak LS_64(tcp->vlan_tag, IRDMAQPC_VLANTAG) | 1077*cdcd52d4SBartosz Sobczak LS_64(tcp->arp_idx, IRDMAQPC_ARPIDX)); 1078*cdcd52d4SBartosz Sobczak qw7 |= LS_64(tcp->flow_label, IRDMAQPC_FLOWLABEL) | 1079*cdcd52d4SBartosz Sobczak LS_64(tcp->wscale, IRDMAQPC_WSCALE) | 1080*cdcd52d4SBartosz Sobczak LS_64(tcp->ignore_tcp_opt, IRDMAQPC_IGNORE_TCP_OPT) | 1081*cdcd52d4SBartosz Sobczak LS_64(tcp->ignore_tcp_uns_opt, 1082*cdcd52d4SBartosz Sobczak IRDMAQPC_IGNORE_TCP_UNS_OPT) | 1083*cdcd52d4SBartosz Sobczak LS_64(tcp->tcp_state, IRDMAQPC_TCPSTATE) | 1084*cdcd52d4SBartosz Sobczak LS_64(tcp->rcv_wscale, IRDMAQPC_RCVSCALE) | 1085*cdcd52d4SBartosz Sobczak LS_64(tcp->snd_wscale, IRDMAQPC_SNDSCALE); 1086*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_72, 1087*cdcd52d4SBartosz Sobczak LS_64(tcp->time_stamp_recent, IRDMAQPC_TIMESTAMP_RECENT) | 1088*cdcd52d4SBartosz Sobczak LS_64(tcp->time_stamp_age, IRDMAQPC_TIMESTAMP_AGE)); 1089*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_80, 1090*cdcd52d4SBartosz Sobczak LS_64(tcp->snd_nxt, IRDMAQPC_SNDNXT) | 1091*cdcd52d4SBartosz Sobczak LS_64(tcp->snd_wnd, IRDMAQPC_SNDWND)); 1092*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_88, 1093*cdcd52d4SBartosz Sobczak LS_64(tcp->rcv_nxt, IRDMAQPC_RCVNXT) | 1094*cdcd52d4SBartosz Sobczak LS_64(tcp->rcv_wnd, IRDMAQPC_RCVWND)); 1095*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_96, 1096*cdcd52d4SBartosz Sobczak LS_64(tcp->snd_max, IRDMAQPC_SNDMAX) | 1097*cdcd52d4SBartosz Sobczak LS_64(tcp->snd_una, IRDMAQPC_SNDUNA)); 1098*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_104, 1099*cdcd52d4SBartosz Sobczak LS_64(tcp->srtt, IRDMAQPC_SRTT) | 1100*cdcd52d4SBartosz Sobczak LS_64(tcp->rtt_var, IRDMAQPC_RTTVAR)); 1101*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_112, 1102*cdcd52d4SBartosz Sobczak LS_64(tcp->ss_thresh, IRDMAQPC_SSTHRESH) | 1103*cdcd52d4SBartosz Sobczak LS_64(tcp->cwnd, IRDMAQPC_CWND)); 1104*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_120, 1105*cdcd52d4SBartosz Sobczak LS_64(tcp->snd_wl1, IRDMAQPC_SNDWL1) | 1106*cdcd52d4SBartosz Sobczak LS_64(tcp->snd_wl2, IRDMAQPC_SNDWL2)); 1107*cdcd52d4SBartosz Sobczak qw16 |= LS_64(tcp->max_snd_window, IRDMAQPC_MAXSNDWND) | 1108*cdcd52d4SBartosz Sobczak LS_64(tcp->rexmit_thresh, IRDMAQPC_REXMIT_THRESH); 1109*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_184, 1110*cdcd52d4SBartosz Sobczak LS_64(tcp->local_ipaddr[3], IRDMAQPC_LOCAL_IPADDR3) | 1111*cdcd52d4SBartosz Sobczak LS_64(tcp->local_ipaddr[2], IRDMAQPC_LOCAL_IPADDR2)); 1112*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_192, 1113*cdcd52d4SBartosz Sobczak LS_64(tcp->local_ipaddr[1], IRDMAQPC_LOCAL_IPADDR1) | 1114*cdcd52d4SBartosz Sobczak LS_64(tcp->local_ipaddr[0], IRDMAQPC_LOCAL_IPADDR0)); 1115*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_200, 1116*cdcd52d4SBartosz Sobczak LS_64(iw->t_high, IRDMAQPC_THIGH) | 1117*cdcd52d4SBartosz Sobczak LS_64(iw->t_low, IRDMAQPC_TLOW)); 1118*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_208, 1119*cdcd52d4SBartosz Sobczak LS_64(info->rem_endpoint_idx, IRDMAQPC_REMENDPOINTIDX)); 1120*cdcd52d4SBartosz Sobczak } 1121*cdcd52d4SBartosz Sobczak 1122*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_0, qw0); 1123*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_24, qw3); 1124*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_56, qw7); 1125*cdcd52d4SBartosz Sobczak set_64bit_val(qp_ctx, IRDMA_BYTE_128, qw16); 1126*cdcd52d4SBartosz Sobczak 1127*cdcd52d4SBartosz Sobczak irdma_debug_buf(qp->dev, IRDMA_DEBUG_WQE, "QP_HOST CTX", qp_ctx, 1128*cdcd52d4SBartosz Sobczak IRDMA_QP_CTX_SIZE); 1129*cdcd52d4SBartosz Sobczak } 1130*cdcd52d4SBartosz Sobczak 1131*cdcd52d4SBartosz Sobczak /** 1132*cdcd52d4SBartosz Sobczak * irdma_sc_alloc_stag - mr stag alloc 1133*cdcd52d4SBartosz Sobczak * @dev: sc device struct 1134*cdcd52d4SBartosz Sobczak * @info: stag info 1135*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 1136*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 1137*cdcd52d4SBartosz Sobczak */ 1138*cdcd52d4SBartosz Sobczak static int 1139*cdcd52d4SBartosz Sobczak irdma_sc_alloc_stag(struct irdma_sc_dev *dev, 1140*cdcd52d4SBartosz Sobczak struct irdma_allocate_stag_info *info, 1141*cdcd52d4SBartosz Sobczak u64 scratch, bool post_sq) 1142*cdcd52d4SBartosz Sobczak { 1143*cdcd52d4SBartosz Sobczak __le64 *wqe; 1144*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 1145*cdcd52d4SBartosz Sobczak u64 hdr; 1146*cdcd52d4SBartosz Sobczak enum irdma_page_size page_size; 1147*cdcd52d4SBartosz Sobczak 1148*cdcd52d4SBartosz Sobczak if (info->page_size == 0x40000000) 1149*cdcd52d4SBartosz Sobczak page_size = IRDMA_PAGE_SIZE_1G; 1150*cdcd52d4SBartosz Sobczak else if (info->page_size == 0x200000) 1151*cdcd52d4SBartosz Sobczak page_size = IRDMA_PAGE_SIZE_2M; 1152*cdcd52d4SBartosz Sobczak else 1153*cdcd52d4SBartosz Sobczak page_size = IRDMA_PAGE_SIZE_4K; 1154*cdcd52d4SBartosz Sobczak 1155*cdcd52d4SBartosz Sobczak cqp = dev->cqp; 1156*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 1157*cdcd52d4SBartosz Sobczak if (!wqe) 1158*cdcd52d4SBartosz Sobczak return -ENOSPC; 1159*cdcd52d4SBartosz Sobczak 1160*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 1161*cdcd52d4SBartosz Sobczak FLD_LS_64(dev, info->pd_id, IRDMA_CQPSQ_STAG_PDID) | 1162*cdcd52d4SBartosz Sobczak LS_64(info->total_len, IRDMA_CQPSQ_STAG_STAGLEN)); 1163*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, 1164*cdcd52d4SBartosz Sobczak LS_64(info->stag_idx, IRDMA_CQPSQ_STAG_IDX)); 1165*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, 1166*cdcd52d4SBartosz Sobczak LS_64(info->hmc_fcn_index, IRDMA_CQPSQ_STAG_HMCFNIDX)); 1167*cdcd52d4SBartosz Sobczak 1168*cdcd52d4SBartosz Sobczak if (info->chunk_size) 1169*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_48, 1170*cdcd52d4SBartosz Sobczak LS_64(info->first_pm_pbl_idx, IRDMA_CQPSQ_STAG_FIRSTPMPBLIDX)); 1171*cdcd52d4SBartosz Sobczak 1172*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMA_CQP_OP_ALLOC_STAG, IRDMA_CQPSQ_OPCODE) | 1173*cdcd52d4SBartosz Sobczak LS_64(1, IRDMA_CQPSQ_STAG_MR) | 1174*cdcd52d4SBartosz Sobczak LS_64(info->access_rights, IRDMA_CQPSQ_STAG_ARIGHTS) | 1175*cdcd52d4SBartosz Sobczak LS_64(info->chunk_size, IRDMA_CQPSQ_STAG_LPBLSIZE) | 1176*cdcd52d4SBartosz Sobczak LS_64(page_size, IRDMA_CQPSQ_STAG_HPAGESIZE) | 1177*cdcd52d4SBartosz Sobczak LS_64(info->remote_access, IRDMA_CQPSQ_STAG_REMACCENABLED) | 1178*cdcd52d4SBartosz Sobczak LS_64(info->use_hmc_fcn_index, IRDMA_CQPSQ_STAG_USEHMCFNIDX) | 1179*cdcd52d4SBartosz Sobczak LS_64(info->use_pf_rid, IRDMA_CQPSQ_STAG_USEPFRID) | 1180*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 1181*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 1182*cdcd52d4SBartosz Sobczak 1183*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 1184*cdcd52d4SBartosz Sobczak 1185*cdcd52d4SBartosz Sobczak irdma_debug_buf(dev, IRDMA_DEBUG_WQE, "ALLOC_STAG WQE", wqe, 1186*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 1187*cdcd52d4SBartosz Sobczak if (post_sq) 1188*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 1189*cdcd52d4SBartosz Sobczak 1190*cdcd52d4SBartosz Sobczak return 0; 1191*cdcd52d4SBartosz Sobczak } 1192*cdcd52d4SBartosz Sobczak 1193*cdcd52d4SBartosz Sobczak /** 1194*cdcd52d4SBartosz Sobczak * irdma_sc_mr_reg_non_shared - non-shared mr registration 1195*cdcd52d4SBartosz Sobczak * @dev: sc device struct 1196*cdcd52d4SBartosz Sobczak * @info: mr info 1197*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 1198*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 1199*cdcd52d4SBartosz Sobczak */ 1200*cdcd52d4SBartosz Sobczak static int 1201*cdcd52d4SBartosz Sobczak irdma_sc_mr_reg_non_shared(struct irdma_sc_dev *dev, 1202*cdcd52d4SBartosz Sobczak struct irdma_reg_ns_stag_info *info, 1203*cdcd52d4SBartosz Sobczak u64 scratch, bool post_sq) 1204*cdcd52d4SBartosz Sobczak { 1205*cdcd52d4SBartosz Sobczak __le64 *wqe; 1206*cdcd52d4SBartosz Sobczak u64 fbo; 1207*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 1208*cdcd52d4SBartosz Sobczak u64 hdr; 1209*cdcd52d4SBartosz Sobczak u32 pble_obj_cnt; 1210*cdcd52d4SBartosz Sobczak bool remote_access; 1211*cdcd52d4SBartosz Sobczak u8 addr_type; 1212*cdcd52d4SBartosz Sobczak enum irdma_page_size page_size; 1213*cdcd52d4SBartosz Sobczak 1214*cdcd52d4SBartosz Sobczak if (info->page_size == 0x40000000) 1215*cdcd52d4SBartosz Sobczak page_size = IRDMA_PAGE_SIZE_1G; 1216*cdcd52d4SBartosz Sobczak else if (info->page_size == 0x200000) 1217*cdcd52d4SBartosz Sobczak page_size = IRDMA_PAGE_SIZE_2M; 1218*cdcd52d4SBartosz Sobczak else if (info->page_size == 0x1000) 1219*cdcd52d4SBartosz Sobczak page_size = IRDMA_PAGE_SIZE_4K; 1220*cdcd52d4SBartosz Sobczak else 1221*cdcd52d4SBartosz Sobczak return -EINVAL; 1222*cdcd52d4SBartosz Sobczak 1223*cdcd52d4SBartosz Sobczak if (info->access_rights & (IRDMA_ACCESS_FLAGS_REMOTEREAD_ONLY | 1224*cdcd52d4SBartosz Sobczak IRDMA_ACCESS_FLAGS_REMOTEWRITE_ONLY)) 1225*cdcd52d4SBartosz Sobczak remote_access = true; 1226*cdcd52d4SBartosz Sobczak else 1227*cdcd52d4SBartosz Sobczak remote_access = false; 1228*cdcd52d4SBartosz Sobczak 1229*cdcd52d4SBartosz Sobczak pble_obj_cnt = dev->hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].cnt; 1230*cdcd52d4SBartosz Sobczak if (info->chunk_size && info->first_pm_pbl_index >= pble_obj_cnt) 1231*cdcd52d4SBartosz Sobczak return -EINVAL; 1232*cdcd52d4SBartosz Sobczak 1233*cdcd52d4SBartosz Sobczak cqp = dev->cqp; 1234*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 1235*cdcd52d4SBartosz Sobczak if (!wqe) 1236*cdcd52d4SBartosz Sobczak return -ENOSPC; 1237*cdcd52d4SBartosz Sobczak fbo = info->va & (info->page_size - 1); 1238*cdcd52d4SBartosz Sobczak 1239*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_0, 1240*cdcd52d4SBartosz Sobczak (info->addr_type == IRDMA_ADDR_TYPE_VA_BASED ? 1241*cdcd52d4SBartosz Sobczak info->va : fbo)); 1242*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 1243*cdcd52d4SBartosz Sobczak LS_64(info->total_len, IRDMA_CQPSQ_STAG_STAGLEN) | 1244*cdcd52d4SBartosz Sobczak FLD_LS_64(dev, info->pd_id, IRDMA_CQPSQ_STAG_PDID)); 1245*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, 1246*cdcd52d4SBartosz Sobczak LS_64(info->stag_key, IRDMA_CQPSQ_STAG_KEY) | 1247*cdcd52d4SBartosz Sobczak LS_64(info->stag_idx, IRDMA_CQPSQ_STAG_IDX)); 1248*cdcd52d4SBartosz Sobczak if (!info->chunk_size) 1249*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, info->reg_addr_pa); 1250*cdcd52d4SBartosz Sobczak else 1251*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_48, 1252*cdcd52d4SBartosz Sobczak LS_64(info->first_pm_pbl_index, IRDMA_CQPSQ_STAG_FIRSTPMPBLIDX)); 1253*cdcd52d4SBartosz Sobczak 1254*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, info->hmc_fcn_index); 1255*cdcd52d4SBartosz Sobczak 1256*cdcd52d4SBartosz Sobczak addr_type = (info->addr_type == IRDMA_ADDR_TYPE_VA_BASED) ? 1 : 0; 1257*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMA_CQP_OP_REG_MR, IRDMA_CQPSQ_OPCODE) | 1258*cdcd52d4SBartosz Sobczak LS_64(1, IRDMA_CQPSQ_STAG_MR) | 1259*cdcd52d4SBartosz Sobczak LS_64(info->chunk_size, IRDMA_CQPSQ_STAG_LPBLSIZE) | 1260*cdcd52d4SBartosz Sobczak LS_64(page_size, IRDMA_CQPSQ_STAG_HPAGESIZE) | 1261*cdcd52d4SBartosz Sobczak LS_64(info->access_rights, IRDMA_CQPSQ_STAG_ARIGHTS) | 1262*cdcd52d4SBartosz Sobczak LS_64(remote_access, IRDMA_CQPSQ_STAG_REMACCENABLED) | 1263*cdcd52d4SBartosz Sobczak LS_64(addr_type, IRDMA_CQPSQ_STAG_VABASEDTO) | 1264*cdcd52d4SBartosz Sobczak LS_64(info->use_hmc_fcn_index, IRDMA_CQPSQ_STAG_USEHMCFNIDX) | 1265*cdcd52d4SBartosz Sobczak LS_64(info->use_pf_rid, IRDMA_CQPSQ_STAG_USEPFRID) | 1266*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 1267*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 1268*cdcd52d4SBartosz Sobczak 1269*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 1270*cdcd52d4SBartosz Sobczak 1271*cdcd52d4SBartosz Sobczak irdma_debug_buf(dev, IRDMA_DEBUG_WQE, "MR_REG_NS WQE", wqe, 1272*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 1273*cdcd52d4SBartosz Sobczak if (post_sq) 1274*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 1275*cdcd52d4SBartosz Sobczak 1276*cdcd52d4SBartosz Sobczak return 0; 1277*cdcd52d4SBartosz Sobczak } 1278*cdcd52d4SBartosz Sobczak 1279*cdcd52d4SBartosz Sobczak /** 1280*cdcd52d4SBartosz Sobczak * irdma_sc_dealloc_stag - deallocate stag 1281*cdcd52d4SBartosz Sobczak * @dev: sc device struct 1282*cdcd52d4SBartosz Sobczak * @info: dealloc stag info 1283*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 1284*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 1285*cdcd52d4SBartosz Sobczak */ 1286*cdcd52d4SBartosz Sobczak static int 1287*cdcd52d4SBartosz Sobczak irdma_sc_dealloc_stag(struct irdma_sc_dev *dev, 1288*cdcd52d4SBartosz Sobczak struct irdma_dealloc_stag_info *info, 1289*cdcd52d4SBartosz Sobczak u64 scratch, bool post_sq) 1290*cdcd52d4SBartosz Sobczak { 1291*cdcd52d4SBartosz Sobczak u64 hdr; 1292*cdcd52d4SBartosz Sobczak __le64 *wqe; 1293*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 1294*cdcd52d4SBartosz Sobczak 1295*cdcd52d4SBartosz Sobczak cqp = dev->cqp; 1296*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 1297*cdcd52d4SBartosz Sobczak if (!wqe) 1298*cdcd52d4SBartosz Sobczak return -ENOSPC; 1299*cdcd52d4SBartosz Sobczak 1300*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 1301*cdcd52d4SBartosz Sobczak FLD_LS_64(dev, info->pd_id, IRDMA_CQPSQ_STAG_PDID)); 1302*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, 1303*cdcd52d4SBartosz Sobczak LS_64(info->stag_idx, IRDMA_CQPSQ_STAG_IDX)); 1304*cdcd52d4SBartosz Sobczak 1305*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMA_CQP_OP_DEALLOC_STAG, IRDMA_CQPSQ_OPCODE) | 1306*cdcd52d4SBartosz Sobczak LS_64(info->mr, IRDMA_CQPSQ_STAG_MR) | 1307*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 1308*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 1309*cdcd52d4SBartosz Sobczak 1310*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 1311*cdcd52d4SBartosz Sobczak 1312*cdcd52d4SBartosz Sobczak irdma_debug_buf(dev, IRDMA_DEBUG_WQE, "DEALLOC_STAG WQE", wqe, 1313*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 1314*cdcd52d4SBartosz Sobczak if (post_sq) 1315*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 1316*cdcd52d4SBartosz Sobczak 1317*cdcd52d4SBartosz Sobczak return 0; 1318*cdcd52d4SBartosz Sobczak } 1319*cdcd52d4SBartosz Sobczak 1320*cdcd52d4SBartosz Sobczak /** 1321*cdcd52d4SBartosz Sobczak * irdma_sc_mw_alloc - mw allocate 1322*cdcd52d4SBartosz Sobczak * @dev: sc device struct 1323*cdcd52d4SBartosz Sobczak * @info: memory window allocation information 1324*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 1325*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 1326*cdcd52d4SBartosz Sobczak */ 1327*cdcd52d4SBartosz Sobczak static int 1328*cdcd52d4SBartosz Sobczak irdma_sc_mw_alloc(struct irdma_sc_dev *dev, 1329*cdcd52d4SBartosz Sobczak struct irdma_mw_alloc_info *info, u64 scratch, 1330*cdcd52d4SBartosz Sobczak bool post_sq) 1331*cdcd52d4SBartosz Sobczak { 1332*cdcd52d4SBartosz Sobczak u64 hdr; 1333*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 1334*cdcd52d4SBartosz Sobczak __le64 *wqe; 1335*cdcd52d4SBartosz Sobczak 1336*cdcd52d4SBartosz Sobczak cqp = dev->cqp; 1337*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 1338*cdcd52d4SBartosz Sobczak if (!wqe) 1339*cdcd52d4SBartosz Sobczak return -ENOSPC; 1340*cdcd52d4SBartosz Sobczak 1341*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 1342*cdcd52d4SBartosz Sobczak FLD_LS_64(dev, info->pd_id, IRDMA_CQPSQ_STAG_PDID)); 1343*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, 1344*cdcd52d4SBartosz Sobczak LS_64(info->mw_stag_index, IRDMA_CQPSQ_STAG_IDX)); 1345*cdcd52d4SBartosz Sobczak 1346*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMA_CQP_OP_ALLOC_STAG, IRDMA_CQPSQ_OPCODE) | 1347*cdcd52d4SBartosz Sobczak LS_64(info->mw_wide, IRDMA_CQPSQ_STAG_MWTYPE) | 1348*cdcd52d4SBartosz Sobczak LS_64(info->mw1_bind_dont_vldt_key, 1349*cdcd52d4SBartosz Sobczak IRDMA_CQPSQ_STAG_MW1_BIND_DONT_VLDT_KEY) | 1350*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 1351*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 1352*cdcd52d4SBartosz Sobczak 1353*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 1354*cdcd52d4SBartosz Sobczak 1355*cdcd52d4SBartosz Sobczak irdma_debug_buf(dev, IRDMA_DEBUG_WQE, "MW_ALLOC WQE", wqe, 1356*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 1357*cdcd52d4SBartosz Sobczak if (post_sq) 1358*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 1359*cdcd52d4SBartosz Sobczak 1360*cdcd52d4SBartosz Sobczak return 0; 1361*cdcd52d4SBartosz Sobczak } 1362*cdcd52d4SBartosz Sobczak 1363*cdcd52d4SBartosz Sobczak /** 1364*cdcd52d4SBartosz Sobczak * irdma_sc_mr_fast_register - Posts RDMA fast register mr WR to iwarp qp 1365*cdcd52d4SBartosz Sobczak * @qp: sc qp struct 1366*cdcd52d4SBartosz Sobczak * @info: fast mr info 1367*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 1368*cdcd52d4SBartosz Sobczak */ 1369*cdcd52d4SBartosz Sobczak int 1370*cdcd52d4SBartosz Sobczak irdma_sc_mr_fast_register(struct irdma_sc_qp *qp, 1371*cdcd52d4SBartosz Sobczak struct irdma_fast_reg_stag_info *info, 1372*cdcd52d4SBartosz Sobczak bool post_sq) 1373*cdcd52d4SBartosz Sobczak { 1374*cdcd52d4SBartosz Sobczak u64 temp, hdr; 1375*cdcd52d4SBartosz Sobczak __le64 *wqe; 1376*cdcd52d4SBartosz Sobczak u32 wqe_idx; 1377*cdcd52d4SBartosz Sobczak enum irdma_page_size page_size; 1378*cdcd52d4SBartosz Sobczak struct irdma_post_sq_info sq_info = {0}; 1379*cdcd52d4SBartosz Sobczak 1380*cdcd52d4SBartosz Sobczak if (info->page_size == 0x40000000) 1381*cdcd52d4SBartosz Sobczak page_size = IRDMA_PAGE_SIZE_1G; 1382*cdcd52d4SBartosz Sobczak else if (info->page_size == 0x200000) 1383*cdcd52d4SBartosz Sobczak page_size = IRDMA_PAGE_SIZE_2M; 1384*cdcd52d4SBartosz Sobczak else 1385*cdcd52d4SBartosz Sobczak page_size = IRDMA_PAGE_SIZE_4K; 1386*cdcd52d4SBartosz Sobczak 1387*cdcd52d4SBartosz Sobczak sq_info.wr_id = info->wr_id; 1388*cdcd52d4SBartosz Sobczak sq_info.signaled = info->signaled; 1389*cdcd52d4SBartosz Sobczak sq_info.push_wqe = info->push_wqe; 1390*cdcd52d4SBartosz Sobczak 1391*cdcd52d4SBartosz Sobczak wqe = irdma_qp_get_next_send_wqe(&qp->qp_uk, &wqe_idx, 1392*cdcd52d4SBartosz Sobczak IRDMA_QP_WQE_MIN_QUANTA, 0, &sq_info); 1393*cdcd52d4SBartosz Sobczak if (!wqe) 1394*cdcd52d4SBartosz Sobczak return -ENOSPC; 1395*cdcd52d4SBartosz Sobczak 1396*cdcd52d4SBartosz Sobczak irdma_clr_wqes(&qp->qp_uk, wqe_idx); 1397*cdcd52d4SBartosz Sobczak 1398*cdcd52d4SBartosz Sobczak qp->qp_uk.sq_wrtrk_array[wqe_idx].signaled = info->signaled; 1399*cdcd52d4SBartosz Sobczak irdma_debug(qp->dev, IRDMA_DEBUG_MR, 1400*cdcd52d4SBartosz Sobczak "wr_id[%llxh] wqe_idx[%04d] location[%p]\n", (unsigned long long)info->wr_id, 1401*cdcd52d4SBartosz Sobczak wqe_idx, &qp->qp_uk.sq_wrtrk_array[wqe_idx].wrid); 1402*cdcd52d4SBartosz Sobczak 1403*cdcd52d4SBartosz Sobczak temp = (info->addr_type == IRDMA_ADDR_TYPE_VA_BASED) ? 1404*cdcd52d4SBartosz Sobczak (uintptr_t)info->va : info->fbo; 1405*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_0, temp); 1406*cdcd52d4SBartosz Sobczak 1407*cdcd52d4SBartosz Sobczak temp = RS_64(info->first_pm_pbl_index >> 16, IRDMAQPSQ_FIRSTPMPBLIDXHI); 1408*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 1409*cdcd52d4SBartosz Sobczak LS_64(temp, IRDMAQPSQ_FIRSTPMPBLIDXHI) | 1410*cdcd52d4SBartosz Sobczak LS_64(info->reg_addr_pa >> IRDMAQPSQ_PBLADDR_S, IRDMAQPSQ_PBLADDR)); 1411*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, 1412*cdcd52d4SBartosz Sobczak info->total_len | 1413*cdcd52d4SBartosz Sobczak LS_64(info->first_pm_pbl_index, IRDMAQPSQ_FIRSTPMPBLIDXLO)); 1414*cdcd52d4SBartosz Sobczak 1415*cdcd52d4SBartosz Sobczak hdr = LS_64(info->stag_key, IRDMAQPSQ_STAGKEY) | 1416*cdcd52d4SBartosz Sobczak LS_64(info->stag_idx, IRDMAQPSQ_STAGINDEX) | 1417*cdcd52d4SBartosz Sobczak LS_64(IRDMAQP_OP_FAST_REGISTER, IRDMAQPSQ_OPCODE) | 1418*cdcd52d4SBartosz Sobczak LS_64(info->chunk_size, IRDMAQPSQ_LPBLSIZE) | 1419*cdcd52d4SBartosz Sobczak LS_64(page_size, IRDMAQPSQ_HPAGESIZE) | 1420*cdcd52d4SBartosz Sobczak LS_64(info->access_rights, IRDMAQPSQ_STAGRIGHTS) | 1421*cdcd52d4SBartosz Sobczak LS_64(info->addr_type, IRDMAQPSQ_VABASEDTO) | 1422*cdcd52d4SBartosz Sobczak LS_64((sq_info.push_wqe ? 1 : 0), IRDMAQPSQ_PUSHWQE) | 1423*cdcd52d4SBartosz Sobczak LS_64(info->read_fence, IRDMAQPSQ_READFENCE) | 1424*cdcd52d4SBartosz Sobczak LS_64(info->local_fence, IRDMAQPSQ_LOCALFENCE) | 1425*cdcd52d4SBartosz Sobczak LS_64(info->signaled, IRDMAQPSQ_SIGCOMPL) | 1426*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.swqe_polarity, IRDMAQPSQ_VALID); 1427*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 1428*cdcd52d4SBartosz Sobczak 1429*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 1430*cdcd52d4SBartosz Sobczak 1431*cdcd52d4SBartosz Sobczak irdma_debug_buf(qp->dev, IRDMA_DEBUG_WQE, "FAST_REG WQE", wqe, 1432*cdcd52d4SBartosz Sobczak IRDMA_QP_WQE_MIN_SIZE); 1433*cdcd52d4SBartosz Sobczak if (sq_info.push_wqe) { 1434*cdcd52d4SBartosz Sobczak irdma_qp_push_wqe(&qp->qp_uk, wqe, IRDMA_QP_WQE_MIN_QUANTA, 1435*cdcd52d4SBartosz Sobczak wqe_idx, post_sq); 1436*cdcd52d4SBartosz Sobczak } else { 1437*cdcd52d4SBartosz Sobczak if (post_sq) 1438*cdcd52d4SBartosz Sobczak irdma_uk_qp_post_wr(&qp->qp_uk); 1439*cdcd52d4SBartosz Sobczak } 1440*cdcd52d4SBartosz Sobczak 1441*cdcd52d4SBartosz Sobczak return 0; 1442*cdcd52d4SBartosz Sobczak } 1443*cdcd52d4SBartosz Sobczak 1444*cdcd52d4SBartosz Sobczak /** 1445*cdcd52d4SBartosz Sobczak * irdma_sc_gen_rts_ae - request AE generated after RTS 1446*cdcd52d4SBartosz Sobczak * @qp: sc qp struct 1447*cdcd52d4SBartosz Sobczak */ 1448*cdcd52d4SBartosz Sobczak static void 1449*cdcd52d4SBartosz Sobczak irdma_sc_gen_rts_ae(struct irdma_sc_qp *qp) 1450*cdcd52d4SBartosz Sobczak { 1451*cdcd52d4SBartosz Sobczak __le64 *wqe; 1452*cdcd52d4SBartosz Sobczak u64 hdr; 1453*cdcd52d4SBartosz Sobczak struct irdma_qp_uk *qp_uk; 1454*cdcd52d4SBartosz Sobczak 1455*cdcd52d4SBartosz Sobczak qp_uk = &qp->qp_uk; 1456*cdcd52d4SBartosz Sobczak 1457*cdcd52d4SBartosz Sobczak wqe = qp_uk->sq_base[1].elem; 1458*cdcd52d4SBartosz Sobczak 1459*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMAQP_OP_NOP, IRDMAQPSQ_OPCODE) | 1460*cdcd52d4SBartosz Sobczak LS_64(1, IRDMAQPSQ_LOCALFENCE) | 1461*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.swqe_polarity, IRDMAQPSQ_VALID); 1462*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 1463*cdcd52d4SBartosz Sobczak 1464*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 1465*cdcd52d4SBartosz Sobczak irdma_debug_buf(qp->dev, IRDMA_DEBUG_QP, "NOP W/LOCAL FENCE WQE", wqe, 1466*cdcd52d4SBartosz Sobczak IRDMA_QP_WQE_MIN_SIZE); 1467*cdcd52d4SBartosz Sobczak 1468*cdcd52d4SBartosz Sobczak wqe = qp_uk->sq_base[2].elem; 1469*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMAQP_OP_GEN_RTS_AE, IRDMAQPSQ_OPCODE) | 1470*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.swqe_polarity, IRDMAQPSQ_VALID); 1471*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 1472*cdcd52d4SBartosz Sobczak 1473*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 1474*cdcd52d4SBartosz Sobczak irdma_debug_buf(qp->dev, IRDMA_DEBUG_QP, "CONN EST WQE", wqe, 1475*cdcd52d4SBartosz Sobczak IRDMA_QP_WQE_MIN_SIZE); 1476*cdcd52d4SBartosz Sobczak } 1477*cdcd52d4SBartosz Sobczak 1478*cdcd52d4SBartosz Sobczak /** 1479*cdcd52d4SBartosz Sobczak * irdma_sc_send_lsmm - send last streaming mode message 1480*cdcd52d4SBartosz Sobczak * @qp: sc qp struct 1481*cdcd52d4SBartosz Sobczak * @lsmm_buf: buffer with lsmm message 1482*cdcd52d4SBartosz Sobczak * @size: size of lsmm buffer 1483*cdcd52d4SBartosz Sobczak * @stag: stag of lsmm buffer 1484*cdcd52d4SBartosz Sobczak */ 1485*cdcd52d4SBartosz Sobczak int 1486*cdcd52d4SBartosz Sobczak irdma_sc_send_lsmm(struct irdma_sc_qp *qp, void *lsmm_buf, u32 size, 1487*cdcd52d4SBartosz Sobczak irdma_stag stag) 1488*cdcd52d4SBartosz Sobczak { 1489*cdcd52d4SBartosz Sobczak __le64 *wqe; 1490*cdcd52d4SBartosz Sobczak u64 hdr; 1491*cdcd52d4SBartosz Sobczak struct irdma_qp_uk *qp_uk; 1492*cdcd52d4SBartosz Sobczak 1493*cdcd52d4SBartosz Sobczak qp_uk = &qp->qp_uk; 1494*cdcd52d4SBartosz Sobczak wqe = qp_uk->sq_base->elem; 1495*cdcd52d4SBartosz Sobczak 1496*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_0, (uintptr_t)lsmm_buf); 1497*cdcd52d4SBartosz Sobczak if (qp->qp_uk.uk_attrs->hw_rev == IRDMA_GEN_1) { 1498*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 1499*cdcd52d4SBartosz Sobczak LS_64(size, IRDMAQPSQ_GEN1_FRAG_LEN) | 1500*cdcd52d4SBartosz Sobczak LS_64(stag, IRDMAQPSQ_GEN1_FRAG_STAG)); 1501*cdcd52d4SBartosz Sobczak } else { 1502*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 1503*cdcd52d4SBartosz Sobczak LS_64(size, IRDMAQPSQ_FRAG_LEN) | 1504*cdcd52d4SBartosz Sobczak LS_64(stag, IRDMAQPSQ_FRAG_STAG) | 1505*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.swqe_polarity, IRDMAQPSQ_VALID)); 1506*cdcd52d4SBartosz Sobczak } 1507*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, 0); 1508*cdcd52d4SBartosz Sobczak 1509*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMAQP_OP_RDMA_SEND, IRDMAQPSQ_OPCODE) | 1510*cdcd52d4SBartosz Sobczak LS_64(1, IRDMAQPSQ_STREAMMODE) | 1511*cdcd52d4SBartosz Sobczak LS_64(1, IRDMAQPSQ_WAITFORRCVPDU) | 1512*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.swqe_polarity, IRDMAQPSQ_VALID); 1513*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 1514*cdcd52d4SBartosz Sobczak 1515*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 1516*cdcd52d4SBartosz Sobczak 1517*cdcd52d4SBartosz Sobczak irdma_debug_buf(qp->dev, IRDMA_DEBUG_WQE, "SEND_LSMM WQE", wqe, 1518*cdcd52d4SBartosz Sobczak IRDMA_QP_WQE_MIN_SIZE); 1519*cdcd52d4SBartosz Sobczak 1520*cdcd52d4SBartosz Sobczak if (qp->dev->hw_attrs.uk_attrs.feature_flags & IRDMA_FEATURE_RTS_AE) 1521*cdcd52d4SBartosz Sobczak irdma_sc_gen_rts_ae(qp); 1522*cdcd52d4SBartosz Sobczak 1523*cdcd52d4SBartosz Sobczak return 0; 1524*cdcd52d4SBartosz Sobczak } 1525*cdcd52d4SBartosz Sobczak 1526*cdcd52d4SBartosz Sobczak /** 1527*cdcd52d4SBartosz Sobczak * irdma_sc_send_lsmm_nostag - for privilege qp 1528*cdcd52d4SBartosz Sobczak * @qp: sc qp struct 1529*cdcd52d4SBartosz Sobczak * @lsmm_buf: buffer with lsmm message 1530*cdcd52d4SBartosz Sobczak * @size: size of lsmm buffer 1531*cdcd52d4SBartosz Sobczak */ 1532*cdcd52d4SBartosz Sobczak int 1533*cdcd52d4SBartosz Sobczak irdma_sc_send_lsmm_nostag(struct irdma_sc_qp *qp, void *lsmm_buf, u32 size) 1534*cdcd52d4SBartosz Sobczak { 1535*cdcd52d4SBartosz Sobczak __le64 *wqe; 1536*cdcd52d4SBartosz Sobczak u64 hdr; 1537*cdcd52d4SBartosz Sobczak struct irdma_qp_uk *qp_uk; 1538*cdcd52d4SBartosz Sobczak 1539*cdcd52d4SBartosz Sobczak qp_uk = &qp->qp_uk; 1540*cdcd52d4SBartosz Sobczak wqe = qp_uk->sq_base->elem; 1541*cdcd52d4SBartosz Sobczak 1542*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_0, (uintptr_t)lsmm_buf); 1543*cdcd52d4SBartosz Sobczak 1544*cdcd52d4SBartosz Sobczak if (qp->qp_uk.uk_attrs->hw_rev == IRDMA_GEN_1) 1545*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 1546*cdcd52d4SBartosz Sobczak LS_64(size, IRDMAQPSQ_GEN1_FRAG_LEN)); 1547*cdcd52d4SBartosz Sobczak else 1548*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 1549*cdcd52d4SBartosz Sobczak LS_64(size, IRDMAQPSQ_FRAG_LEN) | 1550*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.swqe_polarity, IRDMAQPSQ_VALID)); 1551*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, 0); 1552*cdcd52d4SBartosz Sobczak 1553*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMAQP_OP_RDMA_SEND, IRDMAQPSQ_OPCODE) | 1554*cdcd52d4SBartosz Sobczak LS_64(1, IRDMAQPSQ_STREAMMODE) | 1555*cdcd52d4SBartosz Sobczak LS_64(1, IRDMAQPSQ_WAITFORRCVPDU) | 1556*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.swqe_polarity, IRDMAQPSQ_VALID); 1557*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 1558*cdcd52d4SBartosz Sobczak 1559*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 1560*cdcd52d4SBartosz Sobczak 1561*cdcd52d4SBartosz Sobczak irdma_debug_buf(qp->dev, IRDMA_DEBUG_WQE, "SEND_LSMM_NOSTAG WQE", wqe, 1562*cdcd52d4SBartosz Sobczak IRDMA_QP_WQE_MIN_SIZE); 1563*cdcd52d4SBartosz Sobczak 1564*cdcd52d4SBartosz Sobczak return 0; 1565*cdcd52d4SBartosz Sobczak } 1566*cdcd52d4SBartosz Sobczak 1567*cdcd52d4SBartosz Sobczak /** 1568*cdcd52d4SBartosz Sobczak * irdma_sc_send_rtt - send last read0 or write0 1569*cdcd52d4SBartosz Sobczak * @qp: sc qp struct 1570*cdcd52d4SBartosz Sobczak * @read: Do read0 or write0 1571*cdcd52d4SBartosz Sobczak */ 1572*cdcd52d4SBartosz Sobczak int 1573*cdcd52d4SBartosz Sobczak irdma_sc_send_rtt(struct irdma_sc_qp *qp, bool read) 1574*cdcd52d4SBartosz Sobczak { 1575*cdcd52d4SBartosz Sobczak __le64 *wqe; 1576*cdcd52d4SBartosz Sobczak u64 hdr; 1577*cdcd52d4SBartosz Sobczak struct irdma_qp_uk *qp_uk; 1578*cdcd52d4SBartosz Sobczak 1579*cdcd52d4SBartosz Sobczak qp_uk = &qp->qp_uk; 1580*cdcd52d4SBartosz Sobczak wqe = qp_uk->sq_base->elem; 1581*cdcd52d4SBartosz Sobczak 1582*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_0, 0); 1583*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, 0); 1584*cdcd52d4SBartosz Sobczak if (read) { 1585*cdcd52d4SBartosz Sobczak if (qp->qp_uk.uk_attrs->hw_rev == IRDMA_GEN_1) { 1586*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 1587*cdcd52d4SBartosz Sobczak LS_64(0xabcd, IRDMAQPSQ_GEN1_FRAG_STAG)); 1588*cdcd52d4SBartosz Sobczak } else { 1589*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 1590*cdcd52d4SBartosz Sobczak (u64)0xabcd | LS_64(qp->qp_uk.swqe_polarity, 1591*cdcd52d4SBartosz Sobczak IRDMAQPSQ_VALID)); 1592*cdcd52d4SBartosz Sobczak } 1593*cdcd52d4SBartosz Sobczak hdr = LS_64(0x1234, IRDMAQPSQ_REMSTAG) | 1594*cdcd52d4SBartosz Sobczak LS_64(IRDMAQP_OP_RDMA_READ, IRDMAQPSQ_OPCODE) | 1595*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.swqe_polarity, IRDMAQPSQ_VALID); 1596*cdcd52d4SBartosz Sobczak 1597*cdcd52d4SBartosz Sobczak } else { 1598*cdcd52d4SBartosz Sobczak if (qp->qp_uk.uk_attrs->hw_rev == IRDMA_GEN_1) { 1599*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 0); 1600*cdcd52d4SBartosz Sobczak } else { 1601*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, 1602*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.swqe_polarity, 1603*cdcd52d4SBartosz Sobczak IRDMAQPSQ_VALID)); 1604*cdcd52d4SBartosz Sobczak } 1605*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMAQP_OP_RDMA_WRITE, IRDMAQPSQ_OPCODE) | 1606*cdcd52d4SBartosz Sobczak LS_64(qp->qp_uk.swqe_polarity, IRDMAQPSQ_VALID); 1607*cdcd52d4SBartosz Sobczak } 1608*cdcd52d4SBartosz Sobczak 1609*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 1610*cdcd52d4SBartosz Sobczak 1611*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 1612*cdcd52d4SBartosz Sobczak 1613*cdcd52d4SBartosz Sobczak irdma_debug_buf(qp->dev, IRDMA_DEBUG_WQE, "RTR WQE", wqe, 1614*cdcd52d4SBartosz Sobczak IRDMA_QP_WQE_MIN_SIZE); 1615*cdcd52d4SBartosz Sobczak 1616*cdcd52d4SBartosz Sobczak if (qp->dev->hw_attrs.uk_attrs.feature_flags & IRDMA_FEATURE_RTS_AE) 1617*cdcd52d4SBartosz Sobczak irdma_sc_gen_rts_ae(qp); 1618*cdcd52d4SBartosz Sobczak 1619*cdcd52d4SBartosz Sobczak return 0; 1620*cdcd52d4SBartosz Sobczak } 1621*cdcd52d4SBartosz Sobczak 1622*cdcd52d4SBartosz Sobczak /** 1623*cdcd52d4SBartosz Sobczak * irdma_iwarp_opcode - determine if incoming is rdma layer 1624*cdcd52d4SBartosz Sobczak * @info: aeq info for the packet 1625*cdcd52d4SBartosz Sobczak * @pkt: packet for error 1626*cdcd52d4SBartosz Sobczak */ 1627*cdcd52d4SBartosz Sobczak static u32 irdma_iwarp_opcode(struct irdma_aeqe_info *info, u8 *pkt){ 1628*cdcd52d4SBartosz Sobczak BE16 *mpa; 1629*cdcd52d4SBartosz Sobczak u32 opcode = 0xffffffff; 1630*cdcd52d4SBartosz Sobczak 1631*cdcd52d4SBartosz Sobczak if (info->q2_data_written) { 1632*cdcd52d4SBartosz Sobczak mpa = (BE16 *) pkt; 1633*cdcd52d4SBartosz Sobczak opcode = IRDMA_NTOHS(mpa[1]) & 0xf; 1634*cdcd52d4SBartosz Sobczak } 1635*cdcd52d4SBartosz Sobczak 1636*cdcd52d4SBartosz Sobczak return opcode; 1637*cdcd52d4SBartosz Sobczak } 1638*cdcd52d4SBartosz Sobczak 1639*cdcd52d4SBartosz Sobczak /** 1640*cdcd52d4SBartosz Sobczak * irdma_locate_mpa - return pointer to mpa in the pkt 1641*cdcd52d4SBartosz Sobczak * @pkt: packet with data 1642*cdcd52d4SBartosz Sobczak */ 1643*cdcd52d4SBartosz Sobczak static u8 *irdma_locate_mpa(u8 *pkt) { 1644*cdcd52d4SBartosz Sobczak /* skip over ethernet header */ 1645*cdcd52d4SBartosz Sobczak pkt += IRDMA_MAC_HLEN; 1646*cdcd52d4SBartosz Sobczak 1647*cdcd52d4SBartosz Sobczak /* Skip over IP and TCP headers */ 1648*cdcd52d4SBartosz Sobczak pkt += 4 * (pkt[0] & 0x0f); 1649*cdcd52d4SBartosz Sobczak pkt += 4 * ((pkt[12] >> 4) & 0x0f); 1650*cdcd52d4SBartosz Sobczak 1651*cdcd52d4SBartosz Sobczak return pkt; 1652*cdcd52d4SBartosz Sobczak } 1653*cdcd52d4SBartosz Sobczak 1654*cdcd52d4SBartosz Sobczak /** 1655*cdcd52d4SBartosz Sobczak * irdma_bld_termhdr_ctrl - setup terminate hdr control fields 1656*cdcd52d4SBartosz Sobczak * @qp: sc qp ptr for pkt 1657*cdcd52d4SBartosz Sobczak * @hdr: term hdr 1658*cdcd52d4SBartosz Sobczak * @opcode: flush opcode for termhdr 1659*cdcd52d4SBartosz Sobczak * @layer_etype: error layer + error type 1660*cdcd52d4SBartosz Sobczak * @err: error cod ein the header 1661*cdcd52d4SBartosz Sobczak */ 1662*cdcd52d4SBartosz Sobczak static void 1663*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(struct irdma_sc_qp *qp, 1664*cdcd52d4SBartosz Sobczak struct irdma_terminate_hdr *hdr, 1665*cdcd52d4SBartosz Sobczak enum irdma_flush_opcode opcode, 1666*cdcd52d4SBartosz Sobczak u8 layer_etype, u8 err) 1667*cdcd52d4SBartosz Sobczak { 1668*cdcd52d4SBartosz Sobczak qp->flush_code = opcode; 1669*cdcd52d4SBartosz Sobczak hdr->layer_etype = layer_etype; 1670*cdcd52d4SBartosz Sobczak hdr->error_code = err; 1671*cdcd52d4SBartosz Sobczak } 1672*cdcd52d4SBartosz Sobczak 1673*cdcd52d4SBartosz Sobczak /** 1674*cdcd52d4SBartosz Sobczak * irdma_bld_termhdr_ddp_rdma - setup ddp and rdma hdrs in terminate hdr 1675*cdcd52d4SBartosz Sobczak * @pkt: ptr to mpa in offending pkt 1676*cdcd52d4SBartosz Sobczak * @hdr: term hdr 1677*cdcd52d4SBartosz Sobczak * @copy_len: offending pkt length to be copied to term hdr 1678*cdcd52d4SBartosz Sobczak * @is_tagged: DDP tagged or untagged 1679*cdcd52d4SBartosz Sobczak */ 1680*cdcd52d4SBartosz Sobczak static void 1681*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ddp_rdma(u8 *pkt, struct irdma_terminate_hdr *hdr, 1682*cdcd52d4SBartosz Sobczak int *copy_len, u8 *is_tagged) 1683*cdcd52d4SBartosz Sobczak { 1684*cdcd52d4SBartosz Sobczak u16 ddp_seg_len; 1685*cdcd52d4SBartosz Sobczak 1686*cdcd52d4SBartosz Sobczak ddp_seg_len = IRDMA_NTOHS(*(BE16 *) pkt); 1687*cdcd52d4SBartosz Sobczak if (ddp_seg_len) { 1688*cdcd52d4SBartosz Sobczak *copy_len = 2; 1689*cdcd52d4SBartosz Sobczak hdr->hdrct = DDP_LEN_FLAG; 1690*cdcd52d4SBartosz Sobczak if (pkt[2] & 0x80) { 1691*cdcd52d4SBartosz Sobczak *is_tagged = 1; 1692*cdcd52d4SBartosz Sobczak if (ddp_seg_len >= TERM_DDP_LEN_TAGGED) { 1693*cdcd52d4SBartosz Sobczak *copy_len += TERM_DDP_LEN_TAGGED; 1694*cdcd52d4SBartosz Sobczak hdr->hdrct |= DDP_HDR_FLAG; 1695*cdcd52d4SBartosz Sobczak } 1696*cdcd52d4SBartosz Sobczak } else { 1697*cdcd52d4SBartosz Sobczak if (ddp_seg_len >= TERM_DDP_LEN_UNTAGGED) { 1698*cdcd52d4SBartosz Sobczak *copy_len += TERM_DDP_LEN_UNTAGGED; 1699*cdcd52d4SBartosz Sobczak hdr->hdrct |= DDP_HDR_FLAG; 1700*cdcd52d4SBartosz Sobczak } 1701*cdcd52d4SBartosz Sobczak if (ddp_seg_len >= (TERM_DDP_LEN_UNTAGGED + TERM_RDMA_LEN) && 1702*cdcd52d4SBartosz Sobczak ((pkt[3] & RDMA_OPCODE_M) == RDMA_READ_REQ_OPCODE)) { 1703*cdcd52d4SBartosz Sobczak *copy_len += TERM_RDMA_LEN; 1704*cdcd52d4SBartosz Sobczak hdr->hdrct |= RDMA_HDR_FLAG; 1705*cdcd52d4SBartosz Sobczak } 1706*cdcd52d4SBartosz Sobczak } 1707*cdcd52d4SBartosz Sobczak } 1708*cdcd52d4SBartosz Sobczak } 1709*cdcd52d4SBartosz Sobczak 1710*cdcd52d4SBartosz Sobczak /** 1711*cdcd52d4SBartosz Sobczak * irdma_bld_terminate_hdr - build terminate message header 1712*cdcd52d4SBartosz Sobczak * @qp: qp associated with received terminate AE 1713*cdcd52d4SBartosz Sobczak * @info: the struct contiaing AE information 1714*cdcd52d4SBartosz Sobczak */ 1715*cdcd52d4SBartosz Sobczak static int 1716*cdcd52d4SBartosz Sobczak irdma_bld_terminate_hdr(struct irdma_sc_qp *qp, 1717*cdcd52d4SBartosz Sobczak struct irdma_aeqe_info *info) 1718*cdcd52d4SBartosz Sobczak { 1719*cdcd52d4SBartosz Sobczak u8 *pkt = qp->q2_buf + Q2_BAD_FRAME_OFFSET; 1720*cdcd52d4SBartosz Sobczak int copy_len = 0; 1721*cdcd52d4SBartosz Sobczak u8 is_tagged = 0; 1722*cdcd52d4SBartosz Sobczak u32 opcode; 1723*cdcd52d4SBartosz Sobczak struct irdma_terminate_hdr *termhdr; 1724*cdcd52d4SBartosz Sobczak 1725*cdcd52d4SBartosz Sobczak termhdr = (struct irdma_terminate_hdr *)qp->q2_buf; 1726*cdcd52d4SBartosz Sobczak memset(termhdr, 0, Q2_BAD_FRAME_OFFSET); 1727*cdcd52d4SBartosz Sobczak 1728*cdcd52d4SBartosz Sobczak if (info->q2_data_written) { 1729*cdcd52d4SBartosz Sobczak pkt = irdma_locate_mpa(pkt); 1730*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ddp_rdma(pkt, termhdr, ©_len, &is_tagged); 1731*cdcd52d4SBartosz Sobczak } 1732*cdcd52d4SBartosz Sobczak 1733*cdcd52d4SBartosz Sobczak opcode = irdma_iwarp_opcode(info, pkt); 1734*cdcd52d4SBartosz Sobczak qp->event_type = IRDMA_QP_EVENT_CATASTROPHIC; 1735*cdcd52d4SBartosz Sobczak qp->sq_flush_code = info->sq; 1736*cdcd52d4SBartosz Sobczak qp->rq_flush_code = info->rq; 1737*cdcd52d4SBartosz Sobczak 1738*cdcd52d4SBartosz Sobczak switch (info->ae_id) { 1739*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_UNALLOCATED_STAG: 1740*cdcd52d4SBartosz Sobczak qp->event_type = IRDMA_QP_EVENT_ACCESS_ERR; 1741*cdcd52d4SBartosz Sobczak if (opcode == IRDMA_OP_TYPE_RDMA_WRITE) 1742*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_PROT_ERR, 1743*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_TAGGED_BUF, 1744*cdcd52d4SBartosz Sobczak DDP_TAGGED_INV_STAG); 1745*cdcd52d4SBartosz Sobczak else 1746*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_REM_ACCESS_ERR, 1747*cdcd52d4SBartosz Sobczak (LAYER_RDMA << 4) | RDMAP_REMOTE_PROT, 1748*cdcd52d4SBartosz Sobczak RDMAP_INV_STAG); 1749*cdcd52d4SBartosz Sobczak break; 1750*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_BOUNDS_VIOLATION: 1751*cdcd52d4SBartosz Sobczak qp->event_type = IRDMA_QP_EVENT_ACCESS_ERR; 1752*cdcd52d4SBartosz Sobczak if (info->q2_data_written) 1753*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_PROT_ERR, 1754*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_TAGGED_BUF, 1755*cdcd52d4SBartosz Sobczak DDP_TAGGED_BOUNDS); 1756*cdcd52d4SBartosz Sobczak else 1757*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_REM_ACCESS_ERR, 1758*cdcd52d4SBartosz Sobczak (LAYER_RDMA << 4) | RDMAP_REMOTE_PROT, 1759*cdcd52d4SBartosz Sobczak RDMAP_INV_BOUNDS); 1760*cdcd52d4SBartosz Sobczak break; 1761*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_BAD_PD: 1762*cdcd52d4SBartosz Sobczak switch (opcode) { 1763*cdcd52d4SBartosz Sobczak case IRDMA_OP_TYPE_RDMA_WRITE: 1764*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_PROT_ERR, 1765*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_TAGGED_BUF, 1766*cdcd52d4SBartosz Sobczak DDP_TAGGED_UNASSOC_STAG); 1767*cdcd52d4SBartosz Sobczak break; 1768*cdcd52d4SBartosz Sobczak case IRDMA_OP_TYPE_SEND_INV: 1769*cdcd52d4SBartosz Sobczak case IRDMA_OP_TYPE_SEND_SOL_INV: 1770*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_REM_ACCESS_ERR, 1771*cdcd52d4SBartosz Sobczak (LAYER_RDMA << 4) | RDMAP_REMOTE_PROT, 1772*cdcd52d4SBartosz Sobczak RDMAP_CANT_INV_STAG); 1773*cdcd52d4SBartosz Sobczak break; 1774*cdcd52d4SBartosz Sobczak default: 1775*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_REM_ACCESS_ERR, 1776*cdcd52d4SBartosz Sobczak (LAYER_RDMA << 4) | RDMAP_REMOTE_PROT, 1777*cdcd52d4SBartosz Sobczak RDMAP_UNASSOC_STAG); 1778*cdcd52d4SBartosz Sobczak } 1779*cdcd52d4SBartosz Sobczak break; 1780*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_INVALID_STAG: 1781*cdcd52d4SBartosz Sobczak qp->event_type = IRDMA_QP_EVENT_ACCESS_ERR; 1782*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_REM_ACCESS_ERR, 1783*cdcd52d4SBartosz Sobczak (LAYER_RDMA << 4) | RDMAP_REMOTE_PROT, 1784*cdcd52d4SBartosz Sobczak RDMAP_INV_STAG); 1785*cdcd52d4SBartosz Sobczak break; 1786*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_BAD_QP: 1787*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_LOC_QP_OP_ERR, 1788*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_UNTAGGED_BUF, 1789*cdcd52d4SBartosz Sobczak DDP_UNTAGGED_INV_QN); 1790*cdcd52d4SBartosz Sobczak break; 1791*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_BAD_STAG_KEY: 1792*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_BAD_STAG_INDEX: 1793*cdcd52d4SBartosz Sobczak qp->event_type = IRDMA_QP_EVENT_ACCESS_ERR; 1794*cdcd52d4SBartosz Sobczak switch (opcode) { 1795*cdcd52d4SBartosz Sobczak case IRDMA_OP_TYPE_SEND_INV: 1796*cdcd52d4SBartosz Sobczak case IRDMA_OP_TYPE_SEND_SOL_INV: 1797*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_REM_OP_ERR, 1798*cdcd52d4SBartosz Sobczak (LAYER_RDMA << 4) | RDMAP_REMOTE_OP, 1799*cdcd52d4SBartosz Sobczak RDMAP_CANT_INV_STAG); 1800*cdcd52d4SBartosz Sobczak break; 1801*cdcd52d4SBartosz Sobczak default: 1802*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_REM_ACCESS_ERR, 1803*cdcd52d4SBartosz Sobczak (LAYER_RDMA << 4) | RDMAP_REMOTE_OP, 1804*cdcd52d4SBartosz Sobczak RDMAP_INV_STAG); 1805*cdcd52d4SBartosz Sobczak } 1806*cdcd52d4SBartosz Sobczak break; 1807*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_RIGHTS_VIOLATION: 1808*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_INVALIDATE_NO_REMOTE_ACCESS_RIGHTS: 1809*cdcd52d4SBartosz Sobczak case IRDMA_AE_PRIV_OPERATION_DENIED: 1810*cdcd52d4SBartosz Sobczak qp->event_type = IRDMA_QP_EVENT_ACCESS_ERR; 1811*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_REM_ACCESS_ERR, 1812*cdcd52d4SBartosz Sobczak (LAYER_RDMA << 4) | RDMAP_REMOTE_PROT, 1813*cdcd52d4SBartosz Sobczak RDMAP_ACCESS); 1814*cdcd52d4SBartosz Sobczak break; 1815*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_TO_WRAP: 1816*cdcd52d4SBartosz Sobczak qp->event_type = IRDMA_QP_EVENT_ACCESS_ERR; 1817*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_REM_ACCESS_ERR, 1818*cdcd52d4SBartosz Sobczak (LAYER_RDMA << 4) | RDMAP_REMOTE_PROT, 1819*cdcd52d4SBartosz Sobczak RDMAP_TO_WRAP); 1820*cdcd52d4SBartosz Sobczak break; 1821*cdcd52d4SBartosz Sobczak case IRDMA_AE_LLP_RECEIVED_MPA_CRC_ERROR: 1822*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_GENERAL_ERR, 1823*cdcd52d4SBartosz Sobczak (LAYER_MPA << 4) | DDP_LLP, MPA_CRC); 1824*cdcd52d4SBartosz Sobczak break; 1825*cdcd52d4SBartosz Sobczak case IRDMA_AE_LLP_SEGMENT_TOO_SMALL: 1826*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_LOC_LEN_ERR, 1827*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_CATASTROPHIC, 1828*cdcd52d4SBartosz Sobczak DDP_CATASTROPHIC_LOCAL); 1829*cdcd52d4SBartosz Sobczak break; 1830*cdcd52d4SBartosz Sobczak case IRDMA_AE_LCE_QP_CATASTROPHIC: 1831*cdcd52d4SBartosz Sobczak case IRDMA_AE_DDP_NO_L_BIT: 1832*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_FATAL_ERR, 1833*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_CATASTROPHIC, 1834*cdcd52d4SBartosz Sobczak DDP_CATASTROPHIC_LOCAL); 1835*cdcd52d4SBartosz Sobczak break; 1836*cdcd52d4SBartosz Sobczak case IRDMA_AE_DDP_INVALID_MSN_GAP_IN_MSN: 1837*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_GENERAL_ERR, 1838*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_UNTAGGED_BUF, 1839*cdcd52d4SBartosz Sobczak DDP_UNTAGGED_INV_MSN_RANGE); 1840*cdcd52d4SBartosz Sobczak break; 1841*cdcd52d4SBartosz Sobczak case IRDMA_AE_DDP_UBE_DDP_MESSAGE_TOO_LONG_FOR_AVAILABLE_BUFFER: 1842*cdcd52d4SBartosz Sobczak qp->event_type = IRDMA_QP_EVENT_ACCESS_ERR; 1843*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_LOC_LEN_ERR, 1844*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_UNTAGGED_BUF, 1845*cdcd52d4SBartosz Sobczak DDP_UNTAGGED_INV_TOO_LONG); 1846*cdcd52d4SBartosz Sobczak break; 1847*cdcd52d4SBartosz Sobczak case IRDMA_AE_DDP_UBE_INVALID_DDP_VERSION: 1848*cdcd52d4SBartosz Sobczak if (is_tagged) 1849*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_GENERAL_ERR, 1850*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_TAGGED_BUF, 1851*cdcd52d4SBartosz Sobczak DDP_TAGGED_INV_DDP_VER); 1852*cdcd52d4SBartosz Sobczak else 1853*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_GENERAL_ERR, 1854*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_UNTAGGED_BUF, 1855*cdcd52d4SBartosz Sobczak DDP_UNTAGGED_INV_DDP_VER); 1856*cdcd52d4SBartosz Sobczak break; 1857*cdcd52d4SBartosz Sobczak case IRDMA_AE_DDP_UBE_INVALID_MO: 1858*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_GENERAL_ERR, 1859*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_UNTAGGED_BUF, 1860*cdcd52d4SBartosz Sobczak DDP_UNTAGGED_INV_MO); 1861*cdcd52d4SBartosz Sobczak break; 1862*cdcd52d4SBartosz Sobczak case IRDMA_AE_DDP_UBE_INVALID_MSN_NO_BUFFER_AVAILABLE: 1863*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_REM_OP_ERR, 1864*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_UNTAGGED_BUF, 1865*cdcd52d4SBartosz Sobczak DDP_UNTAGGED_INV_MSN_NO_BUF); 1866*cdcd52d4SBartosz Sobczak break; 1867*cdcd52d4SBartosz Sobczak case IRDMA_AE_DDP_UBE_INVALID_QN: 1868*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_GENERAL_ERR, 1869*cdcd52d4SBartosz Sobczak (LAYER_DDP << 4) | DDP_UNTAGGED_BUF, 1870*cdcd52d4SBartosz Sobczak DDP_UNTAGGED_INV_QN); 1871*cdcd52d4SBartosz Sobczak break; 1872*cdcd52d4SBartosz Sobczak case IRDMA_AE_RDMAP_ROE_INVALID_RDMAP_VERSION: 1873*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_GENERAL_ERR, 1874*cdcd52d4SBartosz Sobczak (LAYER_RDMA << 4) | RDMAP_REMOTE_OP, 1875*cdcd52d4SBartosz Sobczak RDMAP_INV_RDMAP_VER); 1876*cdcd52d4SBartosz Sobczak break; 1877*cdcd52d4SBartosz Sobczak default: 1878*cdcd52d4SBartosz Sobczak irdma_bld_termhdr_ctrl(qp, termhdr, FLUSH_FATAL_ERR, 1879*cdcd52d4SBartosz Sobczak (LAYER_RDMA << 4) | RDMAP_REMOTE_OP, 1880*cdcd52d4SBartosz Sobczak RDMAP_UNSPECIFIED); 1881*cdcd52d4SBartosz Sobczak break; 1882*cdcd52d4SBartosz Sobczak } 1883*cdcd52d4SBartosz Sobczak 1884*cdcd52d4SBartosz Sobczak if (copy_len) 1885*cdcd52d4SBartosz Sobczak irdma_memcpy(termhdr + 1, pkt, copy_len); 1886*cdcd52d4SBartosz Sobczak 1887*cdcd52d4SBartosz Sobczak return sizeof(struct irdma_terminate_hdr) + copy_len; 1888*cdcd52d4SBartosz Sobczak } 1889*cdcd52d4SBartosz Sobczak 1890*cdcd52d4SBartosz Sobczak /** 1891*cdcd52d4SBartosz Sobczak * irdma_terminate_send_fin() - Send fin for terminate message 1892*cdcd52d4SBartosz Sobczak * @qp: qp associated with received terminate AE 1893*cdcd52d4SBartosz Sobczak */ 1894*cdcd52d4SBartosz Sobczak void 1895*cdcd52d4SBartosz Sobczak irdma_terminate_send_fin(struct irdma_sc_qp *qp) 1896*cdcd52d4SBartosz Sobczak { 1897*cdcd52d4SBartosz Sobczak irdma_term_modify_qp(qp, IRDMA_QP_STATE_TERMINATE, 1898*cdcd52d4SBartosz Sobczak IRDMAQP_TERM_SEND_FIN_ONLY, 0); 1899*cdcd52d4SBartosz Sobczak } 1900*cdcd52d4SBartosz Sobczak 1901*cdcd52d4SBartosz Sobczak /** 1902*cdcd52d4SBartosz Sobczak * irdma_terminate_connection() - Bad AE and send terminate to remote QP 1903*cdcd52d4SBartosz Sobczak * @qp: qp associated with received terminate AE 1904*cdcd52d4SBartosz Sobczak * @info: the struct contiaing AE information 1905*cdcd52d4SBartosz Sobczak */ 1906*cdcd52d4SBartosz Sobczak void 1907*cdcd52d4SBartosz Sobczak irdma_terminate_connection(struct irdma_sc_qp *qp, 1908*cdcd52d4SBartosz Sobczak struct irdma_aeqe_info *info) 1909*cdcd52d4SBartosz Sobczak { 1910*cdcd52d4SBartosz Sobczak u8 termlen = 0; 1911*cdcd52d4SBartosz Sobczak 1912*cdcd52d4SBartosz Sobczak if (qp->term_flags & IRDMA_TERM_SENT) 1913*cdcd52d4SBartosz Sobczak return; 1914*cdcd52d4SBartosz Sobczak 1915*cdcd52d4SBartosz Sobczak termlen = irdma_bld_terminate_hdr(qp, info); 1916*cdcd52d4SBartosz Sobczak irdma_terminate_start_timer(qp); 1917*cdcd52d4SBartosz Sobczak qp->term_flags |= IRDMA_TERM_SENT; 1918*cdcd52d4SBartosz Sobczak irdma_term_modify_qp(qp, IRDMA_QP_STATE_TERMINATE, 1919*cdcd52d4SBartosz Sobczak IRDMAQP_TERM_SEND_TERM_ONLY, termlen); 1920*cdcd52d4SBartosz Sobczak } 1921*cdcd52d4SBartosz Sobczak 1922*cdcd52d4SBartosz Sobczak /** 1923*cdcd52d4SBartosz Sobczak * irdma_terminate_received - handle terminate received AE 1924*cdcd52d4SBartosz Sobczak * @qp: qp associated with received terminate AE 1925*cdcd52d4SBartosz Sobczak * @info: the struct contiaing AE information 1926*cdcd52d4SBartosz Sobczak */ 1927*cdcd52d4SBartosz Sobczak void 1928*cdcd52d4SBartosz Sobczak irdma_terminate_received(struct irdma_sc_qp *qp, 1929*cdcd52d4SBartosz Sobczak struct irdma_aeqe_info *info) 1930*cdcd52d4SBartosz Sobczak { 1931*cdcd52d4SBartosz Sobczak u8 *pkt = qp->q2_buf + Q2_BAD_FRAME_OFFSET; 1932*cdcd52d4SBartosz Sobczak BE32 *mpa; 1933*cdcd52d4SBartosz Sobczak u8 ddp_ctl; 1934*cdcd52d4SBartosz Sobczak u8 rdma_ctl; 1935*cdcd52d4SBartosz Sobczak u16 aeq_id = 0; 1936*cdcd52d4SBartosz Sobczak struct irdma_terminate_hdr *termhdr; 1937*cdcd52d4SBartosz Sobczak 1938*cdcd52d4SBartosz Sobczak mpa = (BE32 *) irdma_locate_mpa(pkt); 1939*cdcd52d4SBartosz Sobczak if (info->q2_data_written) { 1940*cdcd52d4SBartosz Sobczak /* did not validate the frame - do it now */ 1941*cdcd52d4SBartosz Sobczak ddp_ctl = (ntohl(mpa[0]) >> 8) & 0xff; 1942*cdcd52d4SBartosz Sobczak rdma_ctl = ntohl(mpa[0]) & 0xff; 1943*cdcd52d4SBartosz Sobczak if ((ddp_ctl & 0xc0) != 0x40) 1944*cdcd52d4SBartosz Sobczak aeq_id = IRDMA_AE_LCE_QP_CATASTROPHIC; 1945*cdcd52d4SBartosz Sobczak else if ((ddp_ctl & 0x03) != 1) 1946*cdcd52d4SBartosz Sobczak aeq_id = IRDMA_AE_DDP_UBE_INVALID_DDP_VERSION; 1947*cdcd52d4SBartosz Sobczak else if (ntohl(mpa[2]) != 2) 1948*cdcd52d4SBartosz Sobczak aeq_id = IRDMA_AE_DDP_UBE_INVALID_QN; 1949*cdcd52d4SBartosz Sobczak else if (ntohl(mpa[3]) != 1) 1950*cdcd52d4SBartosz Sobczak aeq_id = IRDMA_AE_DDP_INVALID_MSN_GAP_IN_MSN; 1951*cdcd52d4SBartosz Sobczak else if (ntohl(mpa[4]) != 0) 1952*cdcd52d4SBartosz Sobczak aeq_id = IRDMA_AE_DDP_UBE_INVALID_MO; 1953*cdcd52d4SBartosz Sobczak else if ((rdma_ctl & 0xc0) != 0x40) 1954*cdcd52d4SBartosz Sobczak aeq_id = IRDMA_AE_RDMAP_ROE_INVALID_RDMAP_VERSION; 1955*cdcd52d4SBartosz Sobczak 1956*cdcd52d4SBartosz Sobczak info->ae_id = aeq_id; 1957*cdcd52d4SBartosz Sobczak if (info->ae_id) { 1958*cdcd52d4SBartosz Sobczak /* Bad terminate recvd - send back a terminate */ 1959*cdcd52d4SBartosz Sobczak irdma_terminate_connection(qp, info); 1960*cdcd52d4SBartosz Sobczak return; 1961*cdcd52d4SBartosz Sobczak } 1962*cdcd52d4SBartosz Sobczak } 1963*cdcd52d4SBartosz Sobczak 1964*cdcd52d4SBartosz Sobczak qp->term_flags |= IRDMA_TERM_RCVD; 1965*cdcd52d4SBartosz Sobczak qp->event_type = IRDMA_QP_EVENT_CATASTROPHIC; 1966*cdcd52d4SBartosz Sobczak termhdr = (struct irdma_terminate_hdr *)&mpa[5]; 1967*cdcd52d4SBartosz Sobczak if (termhdr->layer_etype == RDMAP_REMOTE_PROT || 1968*cdcd52d4SBartosz Sobczak termhdr->layer_etype == RDMAP_REMOTE_OP) { 1969*cdcd52d4SBartosz Sobczak irdma_terminate_done(qp, 0); 1970*cdcd52d4SBartosz Sobczak } else { 1971*cdcd52d4SBartosz Sobczak irdma_terminate_start_timer(qp); 1972*cdcd52d4SBartosz Sobczak irdma_terminate_send_fin(qp); 1973*cdcd52d4SBartosz Sobczak } 1974*cdcd52d4SBartosz Sobczak } 1975*cdcd52d4SBartosz Sobczak 1976*cdcd52d4SBartosz Sobczak static int 1977*cdcd52d4SBartosz Sobczak irdma_null_ws_add(struct irdma_sc_vsi *vsi, u8 user_pri) 1978*cdcd52d4SBartosz Sobczak { 1979*cdcd52d4SBartosz Sobczak return 0; 1980*cdcd52d4SBartosz Sobczak } 1981*cdcd52d4SBartosz Sobczak 1982*cdcd52d4SBartosz Sobczak static void 1983*cdcd52d4SBartosz Sobczak irdma_null_ws_remove(struct irdma_sc_vsi *vsi, u8 user_pri) 1984*cdcd52d4SBartosz Sobczak { 1985*cdcd52d4SBartosz Sobczak /* do nothing */ 1986*cdcd52d4SBartosz Sobczak } 1987*cdcd52d4SBartosz Sobczak 1988*cdcd52d4SBartosz Sobczak static void 1989*cdcd52d4SBartosz Sobczak irdma_null_ws_reset(struct irdma_sc_vsi *vsi) 1990*cdcd52d4SBartosz Sobczak { 1991*cdcd52d4SBartosz Sobczak /* do nothing */ 1992*cdcd52d4SBartosz Sobczak } 1993*cdcd52d4SBartosz Sobczak 1994*cdcd52d4SBartosz Sobczak /** 1995*cdcd52d4SBartosz Sobczak * irdma_sc_vsi_init - Init the vsi structure 1996*cdcd52d4SBartosz Sobczak * @vsi: pointer to vsi structure to initialize 1997*cdcd52d4SBartosz Sobczak * @info: the info used to initialize the vsi struct 1998*cdcd52d4SBartosz Sobczak */ 1999*cdcd52d4SBartosz Sobczak void 2000*cdcd52d4SBartosz Sobczak irdma_sc_vsi_init(struct irdma_sc_vsi *vsi, 2001*cdcd52d4SBartosz Sobczak struct irdma_vsi_init_info *info) 2002*cdcd52d4SBartosz Sobczak { 2003*cdcd52d4SBartosz Sobczak u8 i; 2004*cdcd52d4SBartosz Sobczak 2005*cdcd52d4SBartosz Sobczak vsi->dev = info->dev; 2006*cdcd52d4SBartosz Sobczak vsi->back_vsi = info->back_vsi; 2007*cdcd52d4SBartosz Sobczak vsi->register_qset = info->register_qset; 2008*cdcd52d4SBartosz Sobczak vsi->unregister_qset = info->unregister_qset; 2009*cdcd52d4SBartosz Sobczak vsi->mtu = info->params->mtu; 2010*cdcd52d4SBartosz Sobczak vsi->exception_lan_q = info->exception_lan_q; 2011*cdcd52d4SBartosz Sobczak vsi->vsi_idx = info->pf_data_vsi_num; 2012*cdcd52d4SBartosz Sobczak if (vsi->dev->hw_attrs.uk_attrs.hw_rev == IRDMA_GEN_1) 2013*cdcd52d4SBartosz Sobczak vsi->fcn_id = info->dev->hmc_fn_id; 2014*cdcd52d4SBartosz Sobczak 2015*cdcd52d4SBartosz Sobczak irdma_set_qos_info(vsi, info->params); 2016*cdcd52d4SBartosz Sobczak for (i = 0; i < IRDMA_MAX_USER_PRIORITY; i++) { 2017*cdcd52d4SBartosz Sobczak mutex_init(&vsi->qos[i].qos_mutex); 2018*cdcd52d4SBartosz Sobczak INIT_LIST_HEAD(&vsi->qos[i].qplist); 2019*cdcd52d4SBartosz Sobczak } 2020*cdcd52d4SBartosz Sobczak if (vsi->register_qset) { 2021*cdcd52d4SBartosz Sobczak vsi->dev->ws_add = irdma_ws_add; 2022*cdcd52d4SBartosz Sobczak vsi->dev->ws_remove = irdma_ws_remove; 2023*cdcd52d4SBartosz Sobczak vsi->dev->ws_reset = irdma_ws_reset; 2024*cdcd52d4SBartosz Sobczak } else { 2025*cdcd52d4SBartosz Sobczak vsi->dev->ws_add = irdma_null_ws_add; 2026*cdcd52d4SBartosz Sobczak vsi->dev->ws_remove = irdma_null_ws_remove; 2027*cdcd52d4SBartosz Sobczak vsi->dev->ws_reset = irdma_null_ws_reset; 2028*cdcd52d4SBartosz Sobczak } 2029*cdcd52d4SBartosz Sobczak } 2030*cdcd52d4SBartosz Sobczak 2031*cdcd52d4SBartosz Sobczak /** 2032*cdcd52d4SBartosz Sobczak * irdma_get_fcn_id - Return the function id 2033*cdcd52d4SBartosz Sobczak * @vsi: pointer to the vsi 2034*cdcd52d4SBartosz Sobczak */ 2035*cdcd52d4SBartosz Sobczak static u8 irdma_get_fcn_id(struct irdma_sc_vsi *vsi){ 2036*cdcd52d4SBartosz Sobczak struct irdma_stats_inst_info stats_info = {0}; 2037*cdcd52d4SBartosz Sobczak struct irdma_sc_dev *dev = vsi->dev; 2038*cdcd52d4SBartosz Sobczak u8 fcn_id = IRDMA_INVALID_FCN_ID; 2039*cdcd52d4SBartosz Sobczak u8 start_idx, max_stats, i; 2040*cdcd52d4SBartosz Sobczak 2041*cdcd52d4SBartosz Sobczak if (dev->hw_attrs.uk_attrs.hw_rev != IRDMA_GEN_1) { 2042*cdcd52d4SBartosz Sobczak if (!irdma_cqp_stats_inst_cmd(vsi, IRDMA_OP_STATS_ALLOCATE, 2043*cdcd52d4SBartosz Sobczak &stats_info)) 2044*cdcd52d4SBartosz Sobczak return stats_info.stats_idx; 2045*cdcd52d4SBartosz Sobczak } 2046*cdcd52d4SBartosz Sobczak 2047*cdcd52d4SBartosz Sobczak start_idx = 1; 2048*cdcd52d4SBartosz Sobczak max_stats = 16; 2049*cdcd52d4SBartosz Sobczak for (i = start_idx; i < max_stats; i++) 2050*cdcd52d4SBartosz Sobczak if (!dev->fcn_id_array[i]) { 2051*cdcd52d4SBartosz Sobczak fcn_id = i; 2052*cdcd52d4SBartosz Sobczak dev->fcn_id_array[i] = true; 2053*cdcd52d4SBartosz Sobczak break; 2054*cdcd52d4SBartosz Sobczak } 2055*cdcd52d4SBartosz Sobczak 2056*cdcd52d4SBartosz Sobczak return fcn_id; 2057*cdcd52d4SBartosz Sobczak } 2058*cdcd52d4SBartosz Sobczak 2059*cdcd52d4SBartosz Sobczak /** 2060*cdcd52d4SBartosz Sobczak * irdma_vsi_stats_init - Initialize the vsi statistics 2061*cdcd52d4SBartosz Sobczak * @vsi: pointer to the vsi structure 2062*cdcd52d4SBartosz Sobczak * @info: The info structure used for initialization 2063*cdcd52d4SBartosz Sobczak */ 2064*cdcd52d4SBartosz Sobczak int 2065*cdcd52d4SBartosz Sobczak irdma_vsi_stats_init(struct irdma_sc_vsi *vsi, 2066*cdcd52d4SBartosz Sobczak struct irdma_vsi_stats_info *info) 2067*cdcd52d4SBartosz Sobczak { 2068*cdcd52d4SBartosz Sobczak u8 fcn_id = info->fcn_id; 2069*cdcd52d4SBartosz Sobczak struct irdma_dma_mem *stats_buff_mem; 2070*cdcd52d4SBartosz Sobczak 2071*cdcd52d4SBartosz Sobczak vsi->pestat = info->pestat; 2072*cdcd52d4SBartosz Sobczak vsi->pestat->hw = vsi->dev->hw; 2073*cdcd52d4SBartosz Sobczak vsi->pestat->vsi = vsi; 2074*cdcd52d4SBartosz Sobczak stats_buff_mem = &vsi->pestat->gather_info.stats_buff_mem; 2075*cdcd52d4SBartosz Sobczak stats_buff_mem->size = IRDMA_GATHER_STATS_BUF_SIZE * 2; 2076*cdcd52d4SBartosz Sobczak stats_buff_mem->va = irdma_allocate_dma_mem(vsi->pestat->hw, 2077*cdcd52d4SBartosz Sobczak stats_buff_mem, 2078*cdcd52d4SBartosz Sobczak stats_buff_mem->size, 1); 2079*cdcd52d4SBartosz Sobczak if (!stats_buff_mem->va) 2080*cdcd52d4SBartosz Sobczak return -ENOMEM; 2081*cdcd52d4SBartosz Sobczak 2082*cdcd52d4SBartosz Sobczak vsi->pestat->gather_info.gather_stats_va = stats_buff_mem->va; 2083*cdcd52d4SBartosz Sobczak vsi->pestat->gather_info.last_gather_stats_va = 2084*cdcd52d4SBartosz Sobczak (void *)((uintptr_t)stats_buff_mem->va + 2085*cdcd52d4SBartosz Sobczak IRDMA_GATHER_STATS_BUF_SIZE); 2086*cdcd52d4SBartosz Sobczak 2087*cdcd52d4SBartosz Sobczak irdma_hw_stats_start_timer(vsi); 2088*cdcd52d4SBartosz Sobczak if (info->alloc_fcn_id) 2089*cdcd52d4SBartosz Sobczak fcn_id = irdma_get_fcn_id(vsi); 2090*cdcd52d4SBartosz Sobczak if (fcn_id == IRDMA_INVALID_FCN_ID) 2091*cdcd52d4SBartosz Sobczak goto stats_error; 2092*cdcd52d4SBartosz Sobczak 2093*cdcd52d4SBartosz Sobczak vsi->stats_fcn_id_alloc = info->alloc_fcn_id; 2094*cdcd52d4SBartosz Sobczak vsi->fcn_id = fcn_id; 2095*cdcd52d4SBartosz Sobczak if (info->alloc_fcn_id) { 2096*cdcd52d4SBartosz Sobczak vsi->pestat->gather_info.use_stats_inst = true; 2097*cdcd52d4SBartosz Sobczak vsi->pestat->gather_info.stats_inst_index = fcn_id; 2098*cdcd52d4SBartosz Sobczak } 2099*cdcd52d4SBartosz Sobczak 2100*cdcd52d4SBartosz Sobczak return 0; 2101*cdcd52d4SBartosz Sobczak 2102*cdcd52d4SBartosz Sobczak stats_error: 2103*cdcd52d4SBartosz Sobczak irdma_free_dma_mem(vsi->pestat->hw, stats_buff_mem); 2104*cdcd52d4SBartosz Sobczak 2105*cdcd52d4SBartosz Sobczak return -EIO; 2106*cdcd52d4SBartosz Sobczak } 2107*cdcd52d4SBartosz Sobczak 2108*cdcd52d4SBartosz Sobczak /** 2109*cdcd52d4SBartosz Sobczak * irdma_vsi_stats_free - Free the vsi stats 2110*cdcd52d4SBartosz Sobczak * @vsi: pointer to the vsi structure 2111*cdcd52d4SBartosz Sobczak */ 2112*cdcd52d4SBartosz Sobczak void 2113*cdcd52d4SBartosz Sobczak irdma_vsi_stats_free(struct irdma_sc_vsi *vsi) 2114*cdcd52d4SBartosz Sobczak { 2115*cdcd52d4SBartosz Sobczak struct irdma_stats_inst_info stats_info = {0}; 2116*cdcd52d4SBartosz Sobczak u8 fcn_id = vsi->fcn_id; 2117*cdcd52d4SBartosz Sobczak struct irdma_sc_dev *dev = vsi->dev; 2118*cdcd52d4SBartosz Sobczak 2119*cdcd52d4SBartosz Sobczak if (dev->hw_attrs.uk_attrs.hw_rev != IRDMA_GEN_1) { 2120*cdcd52d4SBartosz Sobczak if (vsi->stats_fcn_id_alloc) { 2121*cdcd52d4SBartosz Sobczak stats_info.stats_idx = vsi->fcn_id; 2122*cdcd52d4SBartosz Sobczak irdma_cqp_stats_inst_cmd(vsi, IRDMA_OP_STATS_FREE, 2123*cdcd52d4SBartosz Sobczak &stats_info); 2124*cdcd52d4SBartosz Sobczak } 2125*cdcd52d4SBartosz Sobczak } else { 2126*cdcd52d4SBartosz Sobczak if (vsi->stats_fcn_id_alloc && 2127*cdcd52d4SBartosz Sobczak fcn_id < vsi->dev->hw_attrs.max_stat_inst) 2128*cdcd52d4SBartosz Sobczak vsi->dev->fcn_id_array[fcn_id] = false; 2129*cdcd52d4SBartosz Sobczak } 2130*cdcd52d4SBartosz Sobczak 2131*cdcd52d4SBartosz Sobczak if (!vsi->pestat) 2132*cdcd52d4SBartosz Sobczak return; 2133*cdcd52d4SBartosz Sobczak irdma_hw_stats_stop_timer(vsi); 2134*cdcd52d4SBartosz Sobczak irdma_free_dma_mem(vsi->pestat->hw, 2135*cdcd52d4SBartosz Sobczak &vsi->pestat->gather_info.stats_buff_mem); 2136*cdcd52d4SBartosz Sobczak } 2137*cdcd52d4SBartosz Sobczak 2138*cdcd52d4SBartosz Sobczak /** 2139*cdcd52d4SBartosz Sobczak * irdma_get_encoded_wqe_size - given wq size, returns hardware encoded size 2140*cdcd52d4SBartosz Sobczak * @wqsize: size of the wq (sq, rq) to encoded_size 2141*cdcd52d4SBartosz Sobczak * @queue_type: queue type selected for the calculation algorithm 2142*cdcd52d4SBartosz Sobczak */ 2143*cdcd52d4SBartosz Sobczak u8 2144*cdcd52d4SBartosz Sobczak irdma_get_encoded_wqe_size(u32 wqsize, enum irdma_queue_type queue_type) 2145*cdcd52d4SBartosz Sobczak { 2146*cdcd52d4SBartosz Sobczak u8 encoded_size = 0; 2147*cdcd52d4SBartosz Sobczak 2148*cdcd52d4SBartosz Sobczak /* 2149*cdcd52d4SBartosz Sobczak * cqp sq's hw coded value starts from 1 for size of 4 while it starts from 0 for qp' wq's. 2150*cdcd52d4SBartosz Sobczak */ 2151*cdcd52d4SBartosz Sobczak if (queue_type == IRDMA_QUEUE_TYPE_CQP) 2152*cdcd52d4SBartosz Sobczak encoded_size = 1; 2153*cdcd52d4SBartosz Sobczak wqsize >>= 2; 2154*cdcd52d4SBartosz Sobczak while (wqsize >>= 1) 2155*cdcd52d4SBartosz Sobczak encoded_size++; 2156*cdcd52d4SBartosz Sobczak 2157*cdcd52d4SBartosz Sobczak return encoded_size; 2158*cdcd52d4SBartosz Sobczak } 2159*cdcd52d4SBartosz Sobczak 2160*cdcd52d4SBartosz Sobczak /** 2161*cdcd52d4SBartosz Sobczak * irdma_sc_gather_stats - collect the statistics 2162*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 2163*cdcd52d4SBartosz Sobczak * @info: gather stats info structure 2164*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2165*cdcd52d4SBartosz Sobczak */ 2166*cdcd52d4SBartosz Sobczak static int 2167*cdcd52d4SBartosz Sobczak irdma_sc_gather_stats(struct irdma_sc_cqp *cqp, 2168*cdcd52d4SBartosz Sobczak struct irdma_stats_gather_info *info, 2169*cdcd52d4SBartosz Sobczak u64 scratch) 2170*cdcd52d4SBartosz Sobczak { 2171*cdcd52d4SBartosz Sobczak __le64 *wqe; 2172*cdcd52d4SBartosz Sobczak u64 temp; 2173*cdcd52d4SBartosz Sobczak 2174*cdcd52d4SBartosz Sobczak if (info->stats_buff_mem.size < IRDMA_GATHER_STATS_BUF_SIZE) 2175*cdcd52d4SBartosz Sobczak return -ENOSPC; 2176*cdcd52d4SBartosz Sobczak 2177*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2178*cdcd52d4SBartosz Sobczak if (!wqe) 2179*cdcd52d4SBartosz Sobczak return -ENOSPC; 2180*cdcd52d4SBartosz Sobczak 2181*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, 2182*cdcd52d4SBartosz Sobczak LS_64(info->hmc_fcn_index, IRDMA_CQPSQ_STATS_HMC_FCN_INDEX)); 2183*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, info->stats_buff_mem.pa); 2184*cdcd52d4SBartosz Sobczak 2185*cdcd52d4SBartosz Sobczak temp = LS_64(cqp->polarity, IRDMA_CQPSQ_STATS_WQEVALID) | 2186*cdcd52d4SBartosz Sobczak LS_64(info->use_stats_inst, IRDMA_CQPSQ_STATS_USE_INST) | 2187*cdcd52d4SBartosz Sobczak LS_64(info->stats_inst_index, IRDMA_CQPSQ_STATS_INST_INDEX) | 2188*cdcd52d4SBartosz Sobczak LS_64(info->use_hmc_fcn_index, 2189*cdcd52d4SBartosz Sobczak IRDMA_CQPSQ_STATS_USE_HMC_FCN_INDEX) | 2190*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_GATHER_STATS, IRDMA_CQPSQ_STATS_OP); 2191*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2192*cdcd52d4SBartosz Sobczak 2193*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, temp); 2194*cdcd52d4SBartosz Sobczak 2195*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_STATS, "GATHER_STATS WQE", wqe, 2196*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2197*cdcd52d4SBartosz Sobczak 2198*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2199*cdcd52d4SBartosz Sobczak irdma_debug(cqp->dev, IRDMA_DEBUG_STATS, 2200*cdcd52d4SBartosz Sobczak "CQP SQ head 0x%x tail 0x%x size 0x%x\n", cqp->sq_ring.head, 2201*cdcd52d4SBartosz Sobczak cqp->sq_ring.tail, cqp->sq_ring.size); 2202*cdcd52d4SBartosz Sobczak 2203*cdcd52d4SBartosz Sobczak return 0; 2204*cdcd52d4SBartosz Sobczak } 2205*cdcd52d4SBartosz Sobczak 2206*cdcd52d4SBartosz Sobczak /** 2207*cdcd52d4SBartosz Sobczak * irdma_sc_manage_stats_inst - allocate or free stats instance 2208*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 2209*cdcd52d4SBartosz Sobczak * @info: stats info structure 2210*cdcd52d4SBartosz Sobczak * @alloc: alloc vs. delete flag 2211*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2212*cdcd52d4SBartosz Sobczak */ 2213*cdcd52d4SBartosz Sobczak static int 2214*cdcd52d4SBartosz Sobczak irdma_sc_manage_stats_inst(struct irdma_sc_cqp *cqp, 2215*cdcd52d4SBartosz Sobczak struct irdma_stats_inst_info *info, 2216*cdcd52d4SBartosz Sobczak bool alloc, u64 scratch) 2217*cdcd52d4SBartosz Sobczak { 2218*cdcd52d4SBartosz Sobczak __le64 *wqe; 2219*cdcd52d4SBartosz Sobczak u64 temp; 2220*cdcd52d4SBartosz Sobczak 2221*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2222*cdcd52d4SBartosz Sobczak if (!wqe) 2223*cdcd52d4SBartosz Sobczak return -ENOSPC; 2224*cdcd52d4SBartosz Sobczak 2225*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, 2226*cdcd52d4SBartosz Sobczak LS_64(info->hmc_fn_id, IRDMA_CQPSQ_STATS_HMC_FCN_INDEX)); 2227*cdcd52d4SBartosz Sobczak temp = LS_64(cqp->polarity, IRDMA_CQPSQ_STATS_WQEVALID) | 2228*cdcd52d4SBartosz Sobczak LS_64(alloc, IRDMA_CQPSQ_STATS_ALLOC_INST) | 2229*cdcd52d4SBartosz Sobczak LS_64(info->use_hmc_fcn_index, IRDMA_CQPSQ_STATS_USE_HMC_FCN_INDEX) | 2230*cdcd52d4SBartosz Sobczak LS_64(info->stats_idx, IRDMA_CQPSQ_STATS_INST_INDEX) | 2231*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_MANAGE_STATS, IRDMA_CQPSQ_STATS_OP); 2232*cdcd52d4SBartosz Sobczak 2233*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2234*cdcd52d4SBartosz Sobczak 2235*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, temp); 2236*cdcd52d4SBartosz Sobczak 2237*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "MANAGE_STATS WQE", wqe, 2238*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2239*cdcd52d4SBartosz Sobczak 2240*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2241*cdcd52d4SBartosz Sobczak return 0; 2242*cdcd52d4SBartosz Sobczak } 2243*cdcd52d4SBartosz Sobczak 2244*cdcd52d4SBartosz Sobczak /** 2245*cdcd52d4SBartosz Sobczak * irdma_sc_set_up_map - set the up map table 2246*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 2247*cdcd52d4SBartosz Sobczak * @info: User priority map info 2248*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2249*cdcd52d4SBartosz Sobczak */ 2250*cdcd52d4SBartosz Sobczak static int 2251*cdcd52d4SBartosz Sobczak irdma_sc_set_up_map(struct irdma_sc_cqp *cqp, 2252*cdcd52d4SBartosz Sobczak struct irdma_up_info *info, u64 scratch) 2253*cdcd52d4SBartosz Sobczak { 2254*cdcd52d4SBartosz Sobczak __le64 *wqe; 2255*cdcd52d4SBartosz Sobczak u64 temp; 2256*cdcd52d4SBartosz Sobczak 2257*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2258*cdcd52d4SBartosz Sobczak if (!wqe) 2259*cdcd52d4SBartosz Sobczak return -ENOSPC; 2260*cdcd52d4SBartosz Sobczak 2261*cdcd52d4SBartosz Sobczak temp = info->map[0] | LS_64_1(info->map[1], 8) | 2262*cdcd52d4SBartosz Sobczak LS_64_1(info->map[2], 16) | LS_64_1(info->map[3], 24) | 2263*cdcd52d4SBartosz Sobczak LS_64_1(info->map[4], 32) | LS_64_1(info->map[5], 40) | 2264*cdcd52d4SBartosz Sobczak LS_64_1(info->map[6], 48) | LS_64_1(info->map[7], 56); 2265*cdcd52d4SBartosz Sobczak 2266*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_0, temp); 2267*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, 2268*cdcd52d4SBartosz Sobczak LS_64(info->cnp_up_override, IRDMA_CQPSQ_UP_CNPOVERRIDE) | 2269*cdcd52d4SBartosz Sobczak LS_64(info->hmc_fcn_idx, IRDMA_CQPSQ_UP_HMCFCNIDX)); 2270*cdcd52d4SBartosz Sobczak 2271*cdcd52d4SBartosz Sobczak temp = LS_64(cqp->polarity, IRDMA_CQPSQ_UP_WQEVALID) | 2272*cdcd52d4SBartosz Sobczak LS_64(info->use_vlan, IRDMA_CQPSQ_UP_USEVLAN) | 2273*cdcd52d4SBartosz Sobczak LS_64(info->use_cnp_up_override, IRDMA_CQPSQ_UP_USEOVERRIDE) | 2274*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_UP_MAP, IRDMA_CQPSQ_UP_OP); 2275*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2276*cdcd52d4SBartosz Sobczak 2277*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, temp); 2278*cdcd52d4SBartosz Sobczak 2279*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "UPMAP WQE", wqe, 2280*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2281*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2282*cdcd52d4SBartosz Sobczak 2283*cdcd52d4SBartosz Sobczak return 0; 2284*cdcd52d4SBartosz Sobczak } 2285*cdcd52d4SBartosz Sobczak 2286*cdcd52d4SBartosz Sobczak /** 2287*cdcd52d4SBartosz Sobczak * irdma_sc_manage_ws_node - create/modify/destroy WS node 2288*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 2289*cdcd52d4SBartosz Sobczak * @info: node info structure 2290*cdcd52d4SBartosz Sobczak * @node_op: 0 for add 1 for modify, 2 for delete 2291*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2292*cdcd52d4SBartosz Sobczak */ 2293*cdcd52d4SBartosz Sobczak static int 2294*cdcd52d4SBartosz Sobczak irdma_sc_manage_ws_node(struct irdma_sc_cqp *cqp, 2295*cdcd52d4SBartosz Sobczak struct irdma_ws_node_info *info, 2296*cdcd52d4SBartosz Sobczak enum irdma_ws_node_op node_op, u64 scratch) 2297*cdcd52d4SBartosz Sobczak { 2298*cdcd52d4SBartosz Sobczak __le64 *wqe; 2299*cdcd52d4SBartosz Sobczak u64 temp = 0; 2300*cdcd52d4SBartosz Sobczak 2301*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2302*cdcd52d4SBartosz Sobczak if (!wqe) 2303*cdcd52d4SBartosz Sobczak return -ENOSPC; 2304*cdcd52d4SBartosz Sobczak 2305*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, 2306*cdcd52d4SBartosz Sobczak LS_64(info->vsi, IRDMA_CQPSQ_WS_VSI) | 2307*cdcd52d4SBartosz Sobczak LS_64(info->weight, IRDMA_CQPSQ_WS_WEIGHT)); 2308*cdcd52d4SBartosz Sobczak 2309*cdcd52d4SBartosz Sobczak temp = LS_64(cqp->polarity, IRDMA_CQPSQ_WS_WQEVALID) | 2310*cdcd52d4SBartosz Sobczak LS_64(node_op, IRDMA_CQPSQ_WS_NODEOP) | 2311*cdcd52d4SBartosz Sobczak LS_64(info->enable, IRDMA_CQPSQ_WS_ENABLENODE) | 2312*cdcd52d4SBartosz Sobczak LS_64(info->type_leaf, IRDMA_CQPSQ_WS_NODETYPE) | 2313*cdcd52d4SBartosz Sobczak LS_64(info->prio_type, IRDMA_CQPSQ_WS_PRIOTYPE) | 2314*cdcd52d4SBartosz Sobczak LS_64(info->tc, IRDMA_CQPSQ_WS_TC) | 2315*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_WORK_SCHED_NODE, IRDMA_CQPSQ_WS_OP) | 2316*cdcd52d4SBartosz Sobczak LS_64(info->parent_id, IRDMA_CQPSQ_WS_PARENTID) | 2317*cdcd52d4SBartosz Sobczak LS_64(info->id, IRDMA_CQPSQ_WS_NODEID); 2318*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2319*cdcd52d4SBartosz Sobczak 2320*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, temp); 2321*cdcd52d4SBartosz Sobczak 2322*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "MANAGE_WS WQE", wqe, 2323*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2324*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2325*cdcd52d4SBartosz Sobczak 2326*cdcd52d4SBartosz Sobczak return 0; 2327*cdcd52d4SBartosz Sobczak } 2328*cdcd52d4SBartosz Sobczak 2329*cdcd52d4SBartosz Sobczak /** 2330*cdcd52d4SBartosz Sobczak * irdma_sc_qp_flush_wqes - flush qp's wqe 2331*cdcd52d4SBartosz Sobczak * @qp: sc qp 2332*cdcd52d4SBartosz Sobczak * @info: dlush information 2333*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2334*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 2335*cdcd52d4SBartosz Sobczak */ 2336*cdcd52d4SBartosz Sobczak int 2337*cdcd52d4SBartosz Sobczak irdma_sc_qp_flush_wqes(struct irdma_sc_qp *qp, 2338*cdcd52d4SBartosz Sobczak struct irdma_qp_flush_info *info, u64 scratch, 2339*cdcd52d4SBartosz Sobczak bool post_sq) 2340*cdcd52d4SBartosz Sobczak { 2341*cdcd52d4SBartosz Sobczak u64 temp = 0; 2342*cdcd52d4SBartosz Sobczak __le64 *wqe; 2343*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 2344*cdcd52d4SBartosz Sobczak u64 hdr; 2345*cdcd52d4SBartosz Sobczak bool flush_sq = false, flush_rq = false; 2346*cdcd52d4SBartosz Sobczak 2347*cdcd52d4SBartosz Sobczak if (info->rq && !qp->flush_rq) 2348*cdcd52d4SBartosz Sobczak flush_rq = true; 2349*cdcd52d4SBartosz Sobczak if (info->sq && !qp->flush_sq) 2350*cdcd52d4SBartosz Sobczak flush_sq = true; 2351*cdcd52d4SBartosz Sobczak qp->flush_sq |= flush_sq; 2352*cdcd52d4SBartosz Sobczak qp->flush_rq |= flush_rq; 2353*cdcd52d4SBartosz Sobczak 2354*cdcd52d4SBartosz Sobczak if (!flush_sq && !flush_rq) { 2355*cdcd52d4SBartosz Sobczak irdma_debug(qp->dev, IRDMA_DEBUG_CQP, 2356*cdcd52d4SBartosz Sobczak "Additional flush request ignored for qp %x\n", qp->qp_uk.qp_id); 2357*cdcd52d4SBartosz Sobczak return -EALREADY; 2358*cdcd52d4SBartosz Sobczak } 2359*cdcd52d4SBartosz Sobczak 2360*cdcd52d4SBartosz Sobczak cqp = qp->pd->dev->cqp; 2361*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2362*cdcd52d4SBartosz Sobczak if (!wqe) 2363*cdcd52d4SBartosz Sobczak return -ENOSPC; 2364*cdcd52d4SBartosz Sobczak 2365*cdcd52d4SBartosz Sobczak if (info->userflushcode) { 2366*cdcd52d4SBartosz Sobczak if (flush_rq) 2367*cdcd52d4SBartosz Sobczak temp |= LS_64(info->rq_minor_code, IRDMA_CQPSQ_FWQE_RQMNERR) | 2368*cdcd52d4SBartosz Sobczak LS_64(info->rq_major_code, IRDMA_CQPSQ_FWQE_RQMJERR); 2369*cdcd52d4SBartosz Sobczak if (flush_sq) 2370*cdcd52d4SBartosz Sobczak temp |= LS_64(info->sq_minor_code, IRDMA_CQPSQ_FWQE_SQMNERR) | 2371*cdcd52d4SBartosz Sobczak LS_64(info->sq_major_code, IRDMA_CQPSQ_FWQE_SQMJERR); 2372*cdcd52d4SBartosz Sobczak } 2373*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, temp); 2374*cdcd52d4SBartosz Sobczak 2375*cdcd52d4SBartosz Sobczak temp = (info->generate_ae) ? 2376*cdcd52d4SBartosz Sobczak info->ae_code | LS_64(info->ae_src, IRDMA_CQPSQ_FWQE_AESOURCE) : 0; 2377*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, temp); 2378*cdcd52d4SBartosz Sobczak 2379*cdcd52d4SBartosz Sobczak hdr = qp->qp_uk.qp_id | 2380*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_FLUSH_WQES, IRDMA_CQPSQ_OPCODE) | 2381*cdcd52d4SBartosz Sobczak LS_64(info->generate_ae, IRDMA_CQPSQ_FWQE_GENERATE_AE) | 2382*cdcd52d4SBartosz Sobczak LS_64(info->userflushcode, IRDMA_CQPSQ_FWQE_USERFLCODE) | 2383*cdcd52d4SBartosz Sobczak LS_64(flush_sq, IRDMA_CQPSQ_FWQE_FLUSHSQ) | 2384*cdcd52d4SBartosz Sobczak LS_64(flush_rq, IRDMA_CQPSQ_FWQE_FLUSHRQ) | 2385*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 2386*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2387*cdcd52d4SBartosz Sobczak 2388*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 2389*cdcd52d4SBartosz Sobczak 2390*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "QP_FLUSH WQE", wqe, 2391*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2392*cdcd52d4SBartosz Sobczak if (post_sq) 2393*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2394*cdcd52d4SBartosz Sobczak 2395*cdcd52d4SBartosz Sobczak return 0; 2396*cdcd52d4SBartosz Sobczak } 2397*cdcd52d4SBartosz Sobczak 2398*cdcd52d4SBartosz Sobczak /** 2399*cdcd52d4SBartosz Sobczak * irdma_sc_gen_ae - generate AE, uses flush WQE CQP OP 2400*cdcd52d4SBartosz Sobczak * @qp: sc qp 2401*cdcd52d4SBartosz Sobczak * @info: gen ae information 2402*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2403*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 2404*cdcd52d4SBartosz Sobczak */ 2405*cdcd52d4SBartosz Sobczak static int 2406*cdcd52d4SBartosz Sobczak irdma_sc_gen_ae(struct irdma_sc_qp *qp, 2407*cdcd52d4SBartosz Sobczak struct irdma_gen_ae_info *info, u64 scratch, 2408*cdcd52d4SBartosz Sobczak bool post_sq) 2409*cdcd52d4SBartosz Sobczak { 2410*cdcd52d4SBartosz Sobczak u64 temp; 2411*cdcd52d4SBartosz Sobczak __le64 *wqe; 2412*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 2413*cdcd52d4SBartosz Sobczak u64 hdr; 2414*cdcd52d4SBartosz Sobczak 2415*cdcd52d4SBartosz Sobczak cqp = qp->pd->dev->cqp; 2416*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2417*cdcd52d4SBartosz Sobczak if (!wqe) 2418*cdcd52d4SBartosz Sobczak return -ENOSPC; 2419*cdcd52d4SBartosz Sobczak 2420*cdcd52d4SBartosz Sobczak temp = info->ae_code | LS_64(info->ae_src, IRDMA_CQPSQ_FWQE_AESOURCE); 2421*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, temp); 2422*cdcd52d4SBartosz Sobczak 2423*cdcd52d4SBartosz Sobczak hdr = qp->qp_uk.qp_id | LS_64(IRDMA_CQP_OP_GEN_AE, IRDMA_CQPSQ_OPCODE) | 2424*cdcd52d4SBartosz Sobczak LS_64(1, IRDMA_CQPSQ_FWQE_GENERATE_AE) | 2425*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 2426*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2427*cdcd52d4SBartosz Sobczak 2428*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 2429*cdcd52d4SBartosz Sobczak 2430*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "GEN_AE WQE", wqe, 2431*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2432*cdcd52d4SBartosz Sobczak if (post_sq) 2433*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2434*cdcd52d4SBartosz Sobczak 2435*cdcd52d4SBartosz Sobczak return 0; 2436*cdcd52d4SBartosz Sobczak } 2437*cdcd52d4SBartosz Sobczak 2438*cdcd52d4SBartosz Sobczak /*** irdma_sc_qp_upload_context - upload qp's context 2439*cdcd52d4SBartosz Sobczak * @dev: sc device struct 2440*cdcd52d4SBartosz Sobczak * @info: upload context info ptr for return 2441*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2442*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 2443*cdcd52d4SBartosz Sobczak */ 2444*cdcd52d4SBartosz Sobczak static int 2445*cdcd52d4SBartosz Sobczak irdma_sc_qp_upload_context(struct irdma_sc_dev *dev, 2446*cdcd52d4SBartosz Sobczak struct irdma_upload_context_info *info, 2447*cdcd52d4SBartosz Sobczak u64 scratch, bool post_sq) 2448*cdcd52d4SBartosz Sobczak { 2449*cdcd52d4SBartosz Sobczak __le64 *wqe; 2450*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 2451*cdcd52d4SBartosz Sobczak u64 hdr; 2452*cdcd52d4SBartosz Sobczak 2453*cdcd52d4SBartosz Sobczak cqp = dev->cqp; 2454*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2455*cdcd52d4SBartosz Sobczak if (!wqe) 2456*cdcd52d4SBartosz Sobczak return -ENOSPC; 2457*cdcd52d4SBartosz Sobczak 2458*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, info->buf_pa); 2459*cdcd52d4SBartosz Sobczak 2460*cdcd52d4SBartosz Sobczak hdr = LS_64(info->qp_id, IRDMA_CQPSQ_UCTX_QPID) | 2461*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_UPLOAD_CONTEXT, IRDMA_CQPSQ_OPCODE) | 2462*cdcd52d4SBartosz Sobczak LS_64(info->qp_type, IRDMA_CQPSQ_UCTX_QPTYPE) | 2463*cdcd52d4SBartosz Sobczak LS_64(info->raw_format, IRDMA_CQPSQ_UCTX_RAWFORMAT) | 2464*cdcd52d4SBartosz Sobczak LS_64(info->freeze_qp, IRDMA_CQPSQ_UCTX_FREEZEQP) | 2465*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 2466*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2467*cdcd52d4SBartosz Sobczak 2468*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 2469*cdcd52d4SBartosz Sobczak 2470*cdcd52d4SBartosz Sobczak irdma_debug_buf(dev, IRDMA_DEBUG_WQE, "QP_UPLOAD_CTX WQE", wqe, 2471*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2472*cdcd52d4SBartosz Sobczak if (post_sq) 2473*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2474*cdcd52d4SBartosz Sobczak 2475*cdcd52d4SBartosz Sobczak return 0; 2476*cdcd52d4SBartosz Sobczak } 2477*cdcd52d4SBartosz Sobczak 2478*cdcd52d4SBartosz Sobczak /** 2479*cdcd52d4SBartosz Sobczak * irdma_sc_manage_push_page - Handle push page 2480*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 2481*cdcd52d4SBartosz Sobczak * @info: push page info 2482*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2483*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 2484*cdcd52d4SBartosz Sobczak */ 2485*cdcd52d4SBartosz Sobczak static int 2486*cdcd52d4SBartosz Sobczak irdma_sc_manage_push_page(struct irdma_sc_cqp *cqp, 2487*cdcd52d4SBartosz Sobczak struct irdma_cqp_manage_push_page_info *info, 2488*cdcd52d4SBartosz Sobczak u64 scratch, bool post_sq) 2489*cdcd52d4SBartosz Sobczak { 2490*cdcd52d4SBartosz Sobczak __le64 *wqe; 2491*cdcd52d4SBartosz Sobczak u64 hdr; 2492*cdcd52d4SBartosz Sobczak 2493*cdcd52d4SBartosz Sobczak if (info->free_page && 2494*cdcd52d4SBartosz Sobczak info->push_idx >= cqp->dev->hw_attrs.max_hw_device_pages) 2495*cdcd52d4SBartosz Sobczak return -EINVAL; 2496*cdcd52d4SBartosz Sobczak 2497*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2498*cdcd52d4SBartosz Sobczak if (!wqe) 2499*cdcd52d4SBartosz Sobczak return -ENOSPC; 2500*cdcd52d4SBartosz Sobczak 2501*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, info->qs_handle); 2502*cdcd52d4SBartosz Sobczak hdr = LS_64(info->push_idx, IRDMA_CQPSQ_MPP_PPIDX) | 2503*cdcd52d4SBartosz Sobczak LS_64(info->push_page_type, IRDMA_CQPSQ_MPP_PPTYPE) | 2504*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_MANAGE_PUSH_PAGES, IRDMA_CQPSQ_OPCODE) | 2505*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID) | 2506*cdcd52d4SBartosz Sobczak LS_64(info->free_page, IRDMA_CQPSQ_MPP_FREE_PAGE); 2507*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2508*cdcd52d4SBartosz Sobczak 2509*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 2510*cdcd52d4SBartosz Sobczak 2511*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "MANAGE_PUSH_PAGES WQE", wqe, 2512*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2513*cdcd52d4SBartosz Sobczak if (post_sq) 2514*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2515*cdcd52d4SBartosz Sobczak 2516*cdcd52d4SBartosz Sobczak return 0; 2517*cdcd52d4SBartosz Sobczak } 2518*cdcd52d4SBartosz Sobczak 2519*cdcd52d4SBartosz Sobczak /** 2520*cdcd52d4SBartosz Sobczak * irdma_sc_suspend_qp - suspend qp for param change 2521*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 2522*cdcd52d4SBartosz Sobczak * @qp: sc qp struct 2523*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2524*cdcd52d4SBartosz Sobczak */ 2525*cdcd52d4SBartosz Sobczak static int 2526*cdcd52d4SBartosz Sobczak irdma_sc_suspend_qp(struct irdma_sc_cqp *cqp, struct irdma_sc_qp *qp, 2527*cdcd52d4SBartosz Sobczak u64 scratch) 2528*cdcd52d4SBartosz Sobczak { 2529*cdcd52d4SBartosz Sobczak u64 hdr; 2530*cdcd52d4SBartosz Sobczak __le64 *wqe; 2531*cdcd52d4SBartosz Sobczak 2532*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2533*cdcd52d4SBartosz Sobczak if (!wqe) 2534*cdcd52d4SBartosz Sobczak return -ENOSPC; 2535*cdcd52d4SBartosz Sobczak 2536*cdcd52d4SBartosz Sobczak hdr = LS_64(qp->qp_uk.qp_id, IRDMA_CQPSQ_SUSPENDQP_QPID) | 2537*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_SUSPEND_QP, IRDMA_CQPSQ_OPCODE) | 2538*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 2539*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2540*cdcd52d4SBartosz Sobczak 2541*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 2542*cdcd52d4SBartosz Sobczak 2543*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "SUSPEND_QP WQE", wqe, 2544*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2545*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2546*cdcd52d4SBartosz Sobczak 2547*cdcd52d4SBartosz Sobczak return 0; 2548*cdcd52d4SBartosz Sobczak } 2549*cdcd52d4SBartosz Sobczak 2550*cdcd52d4SBartosz Sobczak /** 2551*cdcd52d4SBartosz Sobczak * irdma_sc_resume_qp - resume qp after suspend 2552*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 2553*cdcd52d4SBartosz Sobczak * @qp: sc qp struct 2554*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2555*cdcd52d4SBartosz Sobczak */ 2556*cdcd52d4SBartosz Sobczak static int 2557*cdcd52d4SBartosz Sobczak irdma_sc_resume_qp(struct irdma_sc_cqp *cqp, struct irdma_sc_qp *qp, 2558*cdcd52d4SBartosz Sobczak u64 scratch) 2559*cdcd52d4SBartosz Sobczak { 2560*cdcd52d4SBartosz Sobczak u64 hdr; 2561*cdcd52d4SBartosz Sobczak __le64 *wqe; 2562*cdcd52d4SBartosz Sobczak 2563*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2564*cdcd52d4SBartosz Sobczak if (!wqe) 2565*cdcd52d4SBartosz Sobczak return -ENOSPC; 2566*cdcd52d4SBartosz Sobczak 2567*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, 2568*cdcd52d4SBartosz Sobczak LS_64(qp->qs_handle, IRDMA_CQPSQ_RESUMEQP_QSHANDLE)); 2569*cdcd52d4SBartosz Sobczak 2570*cdcd52d4SBartosz Sobczak hdr = LS_64(qp->qp_uk.qp_id, IRDMA_CQPSQ_RESUMEQP_QPID) | 2571*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_RESUME_QP, IRDMA_CQPSQ_OPCODE) | 2572*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 2573*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2574*cdcd52d4SBartosz Sobczak 2575*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 2576*cdcd52d4SBartosz Sobczak 2577*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "RESUME_QP WQE", wqe, 2578*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2579*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2580*cdcd52d4SBartosz Sobczak 2581*cdcd52d4SBartosz Sobczak return 0; 2582*cdcd52d4SBartosz Sobczak } 2583*cdcd52d4SBartosz Sobczak 2584*cdcd52d4SBartosz Sobczak /** 2585*cdcd52d4SBartosz Sobczak * irdma_sc_cq_ack - acknowledge completion q 2586*cdcd52d4SBartosz Sobczak * @cq: cq struct 2587*cdcd52d4SBartosz Sobczak */ 2588*cdcd52d4SBartosz Sobczak static inline void 2589*cdcd52d4SBartosz Sobczak irdma_sc_cq_ack(struct irdma_sc_cq *cq) 2590*cdcd52d4SBartosz Sobczak { 2591*cdcd52d4SBartosz Sobczak db_wr32(cq->cq_uk.cq_id, cq->cq_uk.cq_ack_db); 2592*cdcd52d4SBartosz Sobczak } 2593*cdcd52d4SBartosz Sobczak 2594*cdcd52d4SBartosz Sobczak /** 2595*cdcd52d4SBartosz Sobczak * irdma_sc_cq_init - initialize completion q 2596*cdcd52d4SBartosz Sobczak * @cq: cq struct 2597*cdcd52d4SBartosz Sobczak * @info: cq initialization info 2598*cdcd52d4SBartosz Sobczak */ 2599*cdcd52d4SBartosz Sobczak int 2600*cdcd52d4SBartosz Sobczak irdma_sc_cq_init(struct irdma_sc_cq *cq, struct irdma_cq_init_info *info) 2601*cdcd52d4SBartosz Sobczak { 2602*cdcd52d4SBartosz Sobczak int ret_code; 2603*cdcd52d4SBartosz Sobczak u32 pble_obj_cnt; 2604*cdcd52d4SBartosz Sobczak 2605*cdcd52d4SBartosz Sobczak pble_obj_cnt = info->dev->hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].cnt; 2606*cdcd52d4SBartosz Sobczak if (info->virtual_map && info->first_pm_pbl_idx >= pble_obj_cnt) 2607*cdcd52d4SBartosz Sobczak return -EINVAL; 2608*cdcd52d4SBartosz Sobczak 2609*cdcd52d4SBartosz Sobczak cq->cq_pa = info->cq_base_pa; 2610*cdcd52d4SBartosz Sobczak cq->dev = info->dev; 2611*cdcd52d4SBartosz Sobczak cq->ceq_id = info->ceq_id; 2612*cdcd52d4SBartosz Sobczak info->cq_uk_init_info.cqe_alloc_db = cq->dev->cq_arm_db; 2613*cdcd52d4SBartosz Sobczak info->cq_uk_init_info.cq_ack_db = cq->dev->cq_ack_db; 2614*cdcd52d4SBartosz Sobczak ret_code = irdma_uk_cq_init(&cq->cq_uk, &info->cq_uk_init_info); 2615*cdcd52d4SBartosz Sobczak if (ret_code) 2616*cdcd52d4SBartosz Sobczak return ret_code; 2617*cdcd52d4SBartosz Sobczak 2618*cdcd52d4SBartosz Sobczak cq->virtual_map = info->virtual_map; 2619*cdcd52d4SBartosz Sobczak cq->pbl_chunk_size = info->pbl_chunk_size; 2620*cdcd52d4SBartosz Sobczak cq->ceqe_mask = info->ceqe_mask; 2621*cdcd52d4SBartosz Sobczak cq->cq_type = (info->type) ? info->type : IRDMA_CQ_TYPE_IWARP; 2622*cdcd52d4SBartosz Sobczak cq->shadow_area_pa = info->shadow_area_pa; 2623*cdcd52d4SBartosz Sobczak cq->shadow_read_threshold = info->shadow_read_threshold; 2624*cdcd52d4SBartosz Sobczak cq->ceq_id_valid = info->ceq_id_valid; 2625*cdcd52d4SBartosz Sobczak cq->tph_en = info->tph_en; 2626*cdcd52d4SBartosz Sobczak cq->tph_val = info->tph_val; 2627*cdcd52d4SBartosz Sobczak cq->first_pm_pbl_idx = info->first_pm_pbl_idx; 2628*cdcd52d4SBartosz Sobczak cq->vsi = info->vsi; 2629*cdcd52d4SBartosz Sobczak 2630*cdcd52d4SBartosz Sobczak return 0; 2631*cdcd52d4SBartosz Sobczak } 2632*cdcd52d4SBartosz Sobczak 2633*cdcd52d4SBartosz Sobczak /** 2634*cdcd52d4SBartosz Sobczak * irdma_sc_cq_create - create completion q 2635*cdcd52d4SBartosz Sobczak * @cq: cq struct 2636*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2637*cdcd52d4SBartosz Sobczak * @check_overflow: flag for overflow check 2638*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 2639*cdcd52d4SBartosz Sobczak */ 2640*cdcd52d4SBartosz Sobczak static int 2641*cdcd52d4SBartosz Sobczak irdma_sc_cq_create(struct irdma_sc_cq *cq, u64 scratch, 2642*cdcd52d4SBartosz Sobczak bool check_overflow, bool post_sq) 2643*cdcd52d4SBartosz Sobczak { 2644*cdcd52d4SBartosz Sobczak __le64 *wqe; 2645*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 2646*cdcd52d4SBartosz Sobczak u64 hdr; 2647*cdcd52d4SBartosz Sobczak struct irdma_sc_ceq *ceq; 2648*cdcd52d4SBartosz Sobczak int ret_code = 0; 2649*cdcd52d4SBartosz Sobczak 2650*cdcd52d4SBartosz Sobczak cqp = cq->dev->cqp; 2651*cdcd52d4SBartosz Sobczak if (cq->cq_uk.cq_id > (cqp->dev->hmc_info->hmc_obj[IRDMA_HMC_IW_CQ].max_cnt - 1)) 2652*cdcd52d4SBartosz Sobczak return -EINVAL; 2653*cdcd52d4SBartosz Sobczak 2654*cdcd52d4SBartosz Sobczak if (cq->ceq_id > (cq->dev->hmc_fpm_misc.max_ceqs - 1)) 2655*cdcd52d4SBartosz Sobczak return -EINVAL; 2656*cdcd52d4SBartosz Sobczak 2657*cdcd52d4SBartosz Sobczak ceq = cq->dev->ceq[cq->ceq_id]; 2658*cdcd52d4SBartosz Sobczak if (ceq && ceq->reg_cq) 2659*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_add_cq_ctx(ceq, cq); 2660*cdcd52d4SBartosz Sobczak 2661*cdcd52d4SBartosz Sobczak if (ret_code) 2662*cdcd52d4SBartosz Sobczak return ret_code; 2663*cdcd52d4SBartosz Sobczak 2664*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2665*cdcd52d4SBartosz Sobczak if (!wqe) { 2666*cdcd52d4SBartosz Sobczak if (ceq && ceq->reg_cq) 2667*cdcd52d4SBartosz Sobczak irdma_sc_remove_cq_ctx(ceq, cq); 2668*cdcd52d4SBartosz Sobczak return -ENOSPC; 2669*cdcd52d4SBartosz Sobczak } 2670*cdcd52d4SBartosz Sobczak 2671*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_0, cq->cq_uk.cq_size); 2672*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, RS_64_1(cq, 1)); 2673*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, 2674*cdcd52d4SBartosz Sobczak LS_64(cq->shadow_read_threshold, 2675*cdcd52d4SBartosz Sobczak IRDMA_CQPSQ_CQ_SHADOW_READ_THRESHOLD)); 2676*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, (cq->virtual_map ? 0 : cq->cq_pa)); 2677*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, cq->shadow_area_pa); 2678*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_48, 2679*cdcd52d4SBartosz Sobczak LS_64((cq->virtual_map ? cq->first_pm_pbl_idx : 0), 2680*cdcd52d4SBartosz Sobczak IRDMA_CQPSQ_CQ_FIRSTPMPBLIDX)); 2681*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_56, 2682*cdcd52d4SBartosz Sobczak LS_64(cq->tph_val, IRDMA_CQPSQ_TPHVAL) | 2683*cdcd52d4SBartosz Sobczak LS_64(cq->vsi->vsi_idx, IRDMA_CQPSQ_VSIIDX)); 2684*cdcd52d4SBartosz Sobczak 2685*cdcd52d4SBartosz Sobczak hdr = FLD_LS_64(cq->dev, cq->cq_uk.cq_id, IRDMA_CQPSQ_CQ_CQID) | 2686*cdcd52d4SBartosz Sobczak FLD_LS_64(cq->dev, (cq->ceq_id_valid ? cq->ceq_id : 0), 2687*cdcd52d4SBartosz Sobczak IRDMA_CQPSQ_CQ_CEQID) | 2688*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_CREATE_CQ, IRDMA_CQPSQ_OPCODE) | 2689*cdcd52d4SBartosz Sobczak LS_64(cq->pbl_chunk_size, IRDMA_CQPSQ_CQ_LPBLSIZE) | 2690*cdcd52d4SBartosz Sobczak LS_64(check_overflow, IRDMA_CQPSQ_CQ_CHKOVERFLOW) | 2691*cdcd52d4SBartosz Sobczak LS_64(cq->virtual_map, IRDMA_CQPSQ_CQ_VIRTMAP) | 2692*cdcd52d4SBartosz Sobczak LS_64(cq->ceqe_mask, IRDMA_CQPSQ_CQ_ENCEQEMASK) | 2693*cdcd52d4SBartosz Sobczak LS_64(cq->ceq_id_valid, IRDMA_CQPSQ_CQ_CEQIDVALID) | 2694*cdcd52d4SBartosz Sobczak LS_64(cq->tph_en, IRDMA_CQPSQ_TPHEN) | 2695*cdcd52d4SBartosz Sobczak LS_64(cq->cq_uk.avoid_mem_cflct, IRDMA_CQPSQ_CQ_AVOIDMEMCNFLCT) | 2696*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 2697*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2698*cdcd52d4SBartosz Sobczak 2699*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 2700*cdcd52d4SBartosz Sobczak 2701*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "CQ_CREATE WQE", wqe, 2702*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2703*cdcd52d4SBartosz Sobczak if (post_sq) 2704*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2705*cdcd52d4SBartosz Sobczak 2706*cdcd52d4SBartosz Sobczak return 0; 2707*cdcd52d4SBartosz Sobczak } 2708*cdcd52d4SBartosz Sobczak 2709*cdcd52d4SBartosz Sobczak /** 2710*cdcd52d4SBartosz Sobczak * irdma_sc_cq_destroy - destroy completion q 2711*cdcd52d4SBartosz Sobczak * @cq: cq struct 2712*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2713*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 2714*cdcd52d4SBartosz Sobczak */ 2715*cdcd52d4SBartosz Sobczak int 2716*cdcd52d4SBartosz Sobczak irdma_sc_cq_destroy(struct irdma_sc_cq *cq, u64 scratch, bool post_sq) 2717*cdcd52d4SBartosz Sobczak { 2718*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 2719*cdcd52d4SBartosz Sobczak __le64 *wqe; 2720*cdcd52d4SBartosz Sobczak u64 hdr; 2721*cdcd52d4SBartosz Sobczak struct irdma_sc_ceq *ceq; 2722*cdcd52d4SBartosz Sobczak 2723*cdcd52d4SBartosz Sobczak cqp = cq->dev->cqp; 2724*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2725*cdcd52d4SBartosz Sobczak if (!wqe) 2726*cdcd52d4SBartosz Sobczak return -ENOSPC; 2727*cdcd52d4SBartosz Sobczak 2728*cdcd52d4SBartosz Sobczak ceq = cq->dev->ceq[cq->ceq_id]; 2729*cdcd52d4SBartosz Sobczak if (ceq && ceq->reg_cq) 2730*cdcd52d4SBartosz Sobczak irdma_sc_remove_cq_ctx(ceq, cq); 2731*cdcd52d4SBartosz Sobczak 2732*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_0, cq->cq_uk.cq_size); 2733*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, RS_64_1(cq, 1)); 2734*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, cq->shadow_area_pa); 2735*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_48, 2736*cdcd52d4SBartosz Sobczak (cq->virtual_map ? cq->first_pm_pbl_idx : 0)); 2737*cdcd52d4SBartosz Sobczak 2738*cdcd52d4SBartosz Sobczak hdr = cq->cq_uk.cq_id | 2739*cdcd52d4SBartosz Sobczak FLD_LS_64(cq->dev, (cq->ceq_id_valid ? cq->ceq_id : 0), 2740*cdcd52d4SBartosz Sobczak IRDMA_CQPSQ_CQ_CEQID) | 2741*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_DESTROY_CQ, IRDMA_CQPSQ_OPCODE) | 2742*cdcd52d4SBartosz Sobczak LS_64(cq->pbl_chunk_size, IRDMA_CQPSQ_CQ_LPBLSIZE) | 2743*cdcd52d4SBartosz Sobczak LS_64(cq->virtual_map, IRDMA_CQPSQ_CQ_VIRTMAP) | 2744*cdcd52d4SBartosz Sobczak LS_64(cq->ceqe_mask, IRDMA_CQPSQ_CQ_ENCEQEMASK) | 2745*cdcd52d4SBartosz Sobczak LS_64(cq->ceq_id_valid, IRDMA_CQPSQ_CQ_CEQIDVALID) | 2746*cdcd52d4SBartosz Sobczak LS_64(cq->tph_en, IRDMA_CQPSQ_TPHEN) | 2747*cdcd52d4SBartosz Sobczak LS_64(cq->cq_uk.avoid_mem_cflct, IRDMA_CQPSQ_CQ_AVOIDMEMCNFLCT) | 2748*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 2749*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2750*cdcd52d4SBartosz Sobczak 2751*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 2752*cdcd52d4SBartosz Sobczak 2753*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "CQ_DESTROY WQE", wqe, 2754*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2755*cdcd52d4SBartosz Sobczak if (post_sq) 2756*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2757*cdcd52d4SBartosz Sobczak 2758*cdcd52d4SBartosz Sobczak return 0; 2759*cdcd52d4SBartosz Sobczak } 2760*cdcd52d4SBartosz Sobczak 2761*cdcd52d4SBartosz Sobczak /** 2762*cdcd52d4SBartosz Sobczak * irdma_sc_cq_resize - set resized cq buffer info 2763*cdcd52d4SBartosz Sobczak * @cq: resized cq 2764*cdcd52d4SBartosz Sobczak * @info: resized cq buffer info 2765*cdcd52d4SBartosz Sobczak */ 2766*cdcd52d4SBartosz Sobczak void 2767*cdcd52d4SBartosz Sobczak irdma_sc_cq_resize(struct irdma_sc_cq *cq, struct irdma_modify_cq_info *info) 2768*cdcd52d4SBartosz Sobczak { 2769*cdcd52d4SBartosz Sobczak cq->virtual_map = info->virtual_map; 2770*cdcd52d4SBartosz Sobczak cq->cq_pa = info->cq_pa; 2771*cdcd52d4SBartosz Sobczak cq->first_pm_pbl_idx = info->first_pm_pbl_idx; 2772*cdcd52d4SBartosz Sobczak cq->pbl_chunk_size = info->pbl_chunk_size; 2773*cdcd52d4SBartosz Sobczak irdma_uk_cq_resize(&cq->cq_uk, info->cq_base, info->cq_size); 2774*cdcd52d4SBartosz Sobczak } 2775*cdcd52d4SBartosz Sobczak 2776*cdcd52d4SBartosz Sobczak /** 2777*cdcd52d4SBartosz Sobczak * irdma_sc_cq_modify - modify a Completion Queue 2778*cdcd52d4SBartosz Sobczak * @cq: cq struct 2779*cdcd52d4SBartosz Sobczak * @info: modification info struct 2780*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 2781*cdcd52d4SBartosz Sobczak * @post_sq: flag to post to sq 2782*cdcd52d4SBartosz Sobczak */ 2783*cdcd52d4SBartosz Sobczak static int 2784*cdcd52d4SBartosz Sobczak irdma_sc_cq_modify(struct irdma_sc_cq *cq, 2785*cdcd52d4SBartosz Sobczak struct irdma_modify_cq_info *info, u64 scratch, 2786*cdcd52d4SBartosz Sobczak bool post_sq) 2787*cdcd52d4SBartosz Sobczak { 2788*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 2789*cdcd52d4SBartosz Sobczak __le64 *wqe; 2790*cdcd52d4SBartosz Sobczak u64 hdr; 2791*cdcd52d4SBartosz Sobczak u32 pble_obj_cnt; 2792*cdcd52d4SBartosz Sobczak 2793*cdcd52d4SBartosz Sobczak pble_obj_cnt = cq->dev->hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].cnt; 2794*cdcd52d4SBartosz Sobczak if (info->cq_resize && info->virtual_map && 2795*cdcd52d4SBartosz Sobczak info->first_pm_pbl_idx >= pble_obj_cnt) 2796*cdcd52d4SBartosz Sobczak return -EINVAL; 2797*cdcd52d4SBartosz Sobczak 2798*cdcd52d4SBartosz Sobczak cqp = cq->dev->cqp; 2799*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 2800*cdcd52d4SBartosz Sobczak if (!wqe) 2801*cdcd52d4SBartosz Sobczak return -ENOSPC; 2802*cdcd52d4SBartosz Sobczak 2803*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_0, info->cq_size); 2804*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, RS_64_1(cq, 1)); 2805*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, 2806*cdcd52d4SBartosz Sobczak LS_64(info->shadow_read_threshold, 2807*cdcd52d4SBartosz Sobczak IRDMA_CQPSQ_CQ_SHADOW_READ_THRESHOLD)); 2808*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, info->cq_pa); 2809*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, cq->shadow_area_pa); 2810*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_48, info->first_pm_pbl_idx); 2811*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_56, 2812*cdcd52d4SBartosz Sobczak LS_64(cq->tph_val, IRDMA_CQPSQ_TPHVAL) | 2813*cdcd52d4SBartosz Sobczak LS_64(cq->vsi->vsi_idx, IRDMA_CQPSQ_VSIIDX)); 2814*cdcd52d4SBartosz Sobczak 2815*cdcd52d4SBartosz Sobczak hdr = cq->cq_uk.cq_id | 2816*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_MODIFY_CQ, IRDMA_CQPSQ_OPCODE) | 2817*cdcd52d4SBartosz Sobczak LS_64(info->cq_resize, IRDMA_CQPSQ_CQ_CQRESIZE) | 2818*cdcd52d4SBartosz Sobczak LS_64(info->pbl_chunk_size, IRDMA_CQPSQ_CQ_LPBLSIZE) | 2819*cdcd52d4SBartosz Sobczak LS_64(info->check_overflow, IRDMA_CQPSQ_CQ_CHKOVERFLOW) | 2820*cdcd52d4SBartosz Sobczak LS_64(info->virtual_map, IRDMA_CQPSQ_CQ_VIRTMAP) | 2821*cdcd52d4SBartosz Sobczak LS_64(cq->ceqe_mask, IRDMA_CQPSQ_CQ_ENCEQEMASK) | 2822*cdcd52d4SBartosz Sobczak LS_64(cq->tph_en, IRDMA_CQPSQ_TPHEN) | 2823*cdcd52d4SBartosz Sobczak LS_64(cq->cq_uk.avoid_mem_cflct, IRDMA_CQPSQ_CQ_AVOIDMEMCNFLCT) | 2824*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 2825*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 2826*cdcd52d4SBartosz Sobczak 2827*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 2828*cdcd52d4SBartosz Sobczak 2829*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "CQ_MODIFY WQE", wqe, 2830*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 2831*cdcd52d4SBartosz Sobczak if (post_sq) 2832*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 2833*cdcd52d4SBartosz Sobczak 2834*cdcd52d4SBartosz Sobczak return 0; 2835*cdcd52d4SBartosz Sobczak } 2836*cdcd52d4SBartosz Sobczak 2837*cdcd52d4SBartosz Sobczak /** 2838*cdcd52d4SBartosz Sobczak * irdma_check_cqp_progress - check cqp processing progress 2839*cdcd52d4SBartosz Sobczak * @timeout: timeout info struct 2840*cdcd52d4SBartosz Sobczak * @dev: sc device struct 2841*cdcd52d4SBartosz Sobczak */ 2842*cdcd52d4SBartosz Sobczak void 2843*cdcd52d4SBartosz Sobczak irdma_check_cqp_progress(struct irdma_cqp_timeout *timeout, struct irdma_sc_dev *dev) 2844*cdcd52d4SBartosz Sobczak { 2845*cdcd52d4SBartosz Sobczak if (timeout->compl_cqp_cmds != dev->cqp_cmd_stats[IRDMA_OP_CMPL_CMDS]) { 2846*cdcd52d4SBartosz Sobczak timeout->compl_cqp_cmds = dev->cqp_cmd_stats[IRDMA_OP_CMPL_CMDS]; 2847*cdcd52d4SBartosz Sobczak timeout->count = 0; 2848*cdcd52d4SBartosz Sobczak } else { 2849*cdcd52d4SBartosz Sobczak if (dev->cqp_cmd_stats[IRDMA_OP_REQ_CMDS] != 2850*cdcd52d4SBartosz Sobczak timeout->compl_cqp_cmds) 2851*cdcd52d4SBartosz Sobczak timeout->count++; 2852*cdcd52d4SBartosz Sobczak } 2853*cdcd52d4SBartosz Sobczak } 2854*cdcd52d4SBartosz Sobczak 2855*cdcd52d4SBartosz Sobczak /** 2856*cdcd52d4SBartosz Sobczak * irdma_get_cqp_reg_info - get head and tail for cqp using registers 2857*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 2858*cdcd52d4SBartosz Sobczak * @val: cqp tail register value 2859*cdcd52d4SBartosz Sobczak * @tail: wqtail register value 2860*cdcd52d4SBartosz Sobczak * @error: cqp processing err 2861*cdcd52d4SBartosz Sobczak */ 2862*cdcd52d4SBartosz Sobczak static inline void 2863*cdcd52d4SBartosz Sobczak irdma_get_cqp_reg_info(struct irdma_sc_cqp *cqp, u32 *val, 2864*cdcd52d4SBartosz Sobczak u32 *tail, u32 *error) 2865*cdcd52d4SBartosz Sobczak { 2866*cdcd52d4SBartosz Sobczak *val = readl(cqp->dev->hw_regs[IRDMA_CQPTAIL]); 2867*cdcd52d4SBartosz Sobczak *tail = RS_32(*val, IRDMA_CQPTAIL_WQTAIL); 2868*cdcd52d4SBartosz Sobczak *error = RS_32(*val, IRDMA_CQPTAIL_CQP_OP_ERR); 2869*cdcd52d4SBartosz Sobczak } 2870*cdcd52d4SBartosz Sobczak 2871*cdcd52d4SBartosz Sobczak /** 2872*cdcd52d4SBartosz Sobczak * irdma_cqp_poll_registers - poll cqp registers 2873*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 2874*cdcd52d4SBartosz Sobczak * @tail: wqtail register value 2875*cdcd52d4SBartosz Sobczak * @count: how many times to try for completion 2876*cdcd52d4SBartosz Sobczak */ 2877*cdcd52d4SBartosz Sobczak static int 2878*cdcd52d4SBartosz Sobczak irdma_cqp_poll_registers(struct irdma_sc_cqp *cqp, u32 tail, 2879*cdcd52d4SBartosz Sobczak u32 count) 2880*cdcd52d4SBartosz Sobczak { 2881*cdcd52d4SBartosz Sobczak u32 i = 0; 2882*cdcd52d4SBartosz Sobczak u32 newtail, error, val; 2883*cdcd52d4SBartosz Sobczak 2884*cdcd52d4SBartosz Sobczak while (i++ < count) { 2885*cdcd52d4SBartosz Sobczak irdma_get_cqp_reg_info(cqp, &val, &newtail, &error); 2886*cdcd52d4SBartosz Sobczak if (error) { 2887*cdcd52d4SBartosz Sobczak error = readl(cqp->dev->hw_regs[IRDMA_CQPERRCODES]); 2888*cdcd52d4SBartosz Sobczak irdma_debug(cqp->dev, IRDMA_DEBUG_CQP, 2889*cdcd52d4SBartosz Sobczak "CQPERRCODES error_code[x%08X]\n", error); 2890*cdcd52d4SBartosz Sobczak return -EIO; 2891*cdcd52d4SBartosz Sobczak } 2892*cdcd52d4SBartosz Sobczak if (newtail != tail) { 2893*cdcd52d4SBartosz Sobczak /* SUCCESS */ 2894*cdcd52d4SBartosz Sobczak IRDMA_RING_MOVE_TAIL(cqp->sq_ring); 2895*cdcd52d4SBartosz Sobczak cqp->dev->cqp_cmd_stats[IRDMA_OP_CMPL_CMDS]++; 2896*cdcd52d4SBartosz Sobczak return 0; 2897*cdcd52d4SBartosz Sobczak } 2898*cdcd52d4SBartosz Sobczak irdma_usec_delay(cqp->dev->hw_attrs.max_sleep_count); 2899*cdcd52d4SBartosz Sobczak } 2900*cdcd52d4SBartosz Sobczak 2901*cdcd52d4SBartosz Sobczak return -ETIMEDOUT; 2902*cdcd52d4SBartosz Sobczak } 2903*cdcd52d4SBartosz Sobczak 2904*cdcd52d4SBartosz Sobczak /** 2905*cdcd52d4SBartosz Sobczak * irdma_sc_decode_fpm_commit - decode a 64 bit value into count and base 2906*cdcd52d4SBartosz Sobczak * @dev: sc device struct 2907*cdcd52d4SBartosz Sobczak * @buf: pointer to commit buffer 2908*cdcd52d4SBartosz Sobczak * @buf_idx: buffer index 2909*cdcd52d4SBartosz Sobczak * @obj_info: object info pointer 2910*cdcd52d4SBartosz Sobczak * @rsrc_idx: indexs of memory resource 2911*cdcd52d4SBartosz Sobczak */ 2912*cdcd52d4SBartosz Sobczak static u64 irdma_sc_decode_fpm_commit(struct irdma_sc_dev *dev, __le64 * buf, 2913*cdcd52d4SBartosz Sobczak u32 buf_idx, struct irdma_hmc_obj_info *obj_info, 2914*cdcd52d4SBartosz Sobczak u32 rsrc_idx){ 2915*cdcd52d4SBartosz Sobczak u64 temp; 2916*cdcd52d4SBartosz Sobczak 2917*cdcd52d4SBartosz Sobczak get_64bit_val(buf, buf_idx, &temp); 2918*cdcd52d4SBartosz Sobczak 2919*cdcd52d4SBartosz Sobczak switch (rsrc_idx) { 2920*cdcd52d4SBartosz Sobczak case IRDMA_HMC_IW_QP: 2921*cdcd52d4SBartosz Sobczak obj_info[rsrc_idx].cnt = (u32)RS_64(temp, IRDMA_COMMIT_FPM_QPCNT); 2922*cdcd52d4SBartosz Sobczak break; 2923*cdcd52d4SBartosz Sobczak case IRDMA_HMC_IW_CQ: 2924*cdcd52d4SBartosz Sobczak obj_info[rsrc_idx].cnt = (u32)FLD_RS_64(dev, temp, IRDMA_COMMIT_FPM_CQCNT); 2925*cdcd52d4SBartosz Sobczak break; 2926*cdcd52d4SBartosz Sobczak case IRDMA_HMC_IW_APBVT_ENTRY: 2927*cdcd52d4SBartosz Sobczak obj_info[rsrc_idx].cnt = 1; 2928*cdcd52d4SBartosz Sobczak break; 2929*cdcd52d4SBartosz Sobczak default: 2930*cdcd52d4SBartosz Sobczak obj_info[rsrc_idx].cnt = (u32)temp; 2931*cdcd52d4SBartosz Sobczak break; 2932*cdcd52d4SBartosz Sobczak } 2933*cdcd52d4SBartosz Sobczak 2934*cdcd52d4SBartosz Sobczak obj_info[rsrc_idx].base = (u64)RS_64_1(temp, IRDMA_COMMIT_FPM_BASE_S) * 512; 2935*cdcd52d4SBartosz Sobczak 2936*cdcd52d4SBartosz Sobczak return temp; 2937*cdcd52d4SBartosz Sobczak } 2938*cdcd52d4SBartosz Sobczak 2939*cdcd52d4SBartosz Sobczak /** 2940*cdcd52d4SBartosz Sobczak * irdma_sc_parse_fpm_commit_buf - parse fpm commit buffer 2941*cdcd52d4SBartosz Sobczak * @dev: pointer to dev struct 2942*cdcd52d4SBartosz Sobczak * @buf: ptr to fpm commit buffer 2943*cdcd52d4SBartosz Sobczak * @info: ptr to irdma_hmc_obj_info struct 2944*cdcd52d4SBartosz Sobczak * @sd: number of SDs for HMC objects 2945*cdcd52d4SBartosz Sobczak * 2946*cdcd52d4SBartosz Sobczak * parses fpm commit info and copy base value 2947*cdcd52d4SBartosz Sobczak * of hmc objects in hmc_info 2948*cdcd52d4SBartosz Sobczak */ 2949*cdcd52d4SBartosz Sobczak static int 2950*cdcd52d4SBartosz Sobczak irdma_sc_parse_fpm_commit_buf(struct irdma_sc_dev *dev, __le64 * buf, 2951*cdcd52d4SBartosz Sobczak struct irdma_hmc_obj_info *info, 2952*cdcd52d4SBartosz Sobczak u32 *sd) 2953*cdcd52d4SBartosz Sobczak { 2954*cdcd52d4SBartosz Sobczak u64 size; 2955*cdcd52d4SBartosz Sobczak u32 i; 2956*cdcd52d4SBartosz Sobczak u64 max_base = 0; 2957*cdcd52d4SBartosz Sobczak u32 last_hmc_obj = 0; 2958*cdcd52d4SBartosz Sobczak 2959*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_0, info, 2960*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_QP); 2961*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_8, info, 2962*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_CQ); 2963*cdcd52d4SBartosz Sobczak /* skiping RSRVD */ 2964*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_24, info, 2965*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_HTE); 2966*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_32, info, 2967*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_ARP); 2968*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_40, info, 2969*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_APBVT_ENTRY); 2970*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_48, info, 2971*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_MR); 2972*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_56, info, 2973*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_XF); 2974*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_64, info, 2975*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_XFFL); 2976*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_72, info, 2977*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_Q1); 2978*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_80, info, 2979*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_Q1FL); 2980*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_88, info, 2981*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_TIMER); 2982*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_112, info, 2983*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_PBLE); 2984*cdcd52d4SBartosz Sobczak /* skipping RSVD. */ 2985*cdcd52d4SBartosz Sobczak if (dev->hw_attrs.uk_attrs.hw_rev != IRDMA_GEN_1) { 2986*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_96, info, 2987*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_FSIMC); 2988*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_104, info, 2989*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_FSIAV); 2990*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_128, info, 2991*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_RRF); 2992*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_136, info, 2993*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_RRFFL); 2994*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_144, info, 2995*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_HDR); 2996*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_152, info, 2997*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_MD); 2998*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_160, info, 2999*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_OOISC); 3000*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_commit(dev, buf, IRDMA_BYTE_168, info, 3001*cdcd52d4SBartosz Sobczak IRDMA_HMC_IW_OOISCFFL); 3002*cdcd52d4SBartosz Sobczak } 3003*cdcd52d4SBartosz Sobczak 3004*cdcd52d4SBartosz Sobczak /* searching for the last object in HMC to find the size of the HMC area. */ 3005*cdcd52d4SBartosz Sobczak for (i = IRDMA_HMC_IW_QP; i < IRDMA_HMC_IW_MAX; i++) { 3006*cdcd52d4SBartosz Sobczak if (info[i].base > max_base) { 3007*cdcd52d4SBartosz Sobczak max_base = info[i].base; 3008*cdcd52d4SBartosz Sobczak last_hmc_obj = i; 3009*cdcd52d4SBartosz Sobczak } 3010*cdcd52d4SBartosz Sobczak } 3011*cdcd52d4SBartosz Sobczak 3012*cdcd52d4SBartosz Sobczak size = info[last_hmc_obj].cnt * info[last_hmc_obj].size + 3013*cdcd52d4SBartosz Sobczak info[last_hmc_obj].base; 3014*cdcd52d4SBartosz Sobczak 3015*cdcd52d4SBartosz Sobczak if (size & 0x1FFFFF) 3016*cdcd52d4SBartosz Sobczak *sd = (u32)((size >> 21) + 1); /* add 1 for remainder */ 3017*cdcd52d4SBartosz Sobczak else 3018*cdcd52d4SBartosz Sobczak *sd = (u32)(size >> 21); 3019*cdcd52d4SBartosz Sobczak 3020*cdcd52d4SBartosz Sobczak return 0; 3021*cdcd52d4SBartosz Sobczak } 3022*cdcd52d4SBartosz Sobczak 3023*cdcd52d4SBartosz Sobczak /** 3024*cdcd52d4SBartosz Sobczak * irdma_sc_decode_fpm_query() - Decode a 64 bit value into max count and size 3025*cdcd52d4SBartosz Sobczak * @buf: ptr to fpm query buffer 3026*cdcd52d4SBartosz Sobczak * @buf_idx: index into buf 3027*cdcd52d4SBartosz Sobczak * @obj_info: ptr to irdma_hmc_obj_info struct 3028*cdcd52d4SBartosz Sobczak * @rsrc_idx: resource index into info 3029*cdcd52d4SBartosz Sobczak * 3030*cdcd52d4SBartosz Sobczak * Decode a 64 bit value from fpm query buffer into max count and size 3031*cdcd52d4SBartosz Sobczak */ 3032*cdcd52d4SBartosz Sobczak static u64 irdma_sc_decode_fpm_query(__le64 * buf, u32 buf_idx, 3033*cdcd52d4SBartosz Sobczak struct irdma_hmc_obj_info *obj_info, 3034*cdcd52d4SBartosz Sobczak u32 rsrc_idx){ 3035*cdcd52d4SBartosz Sobczak u64 temp; 3036*cdcd52d4SBartosz Sobczak u32 size; 3037*cdcd52d4SBartosz Sobczak 3038*cdcd52d4SBartosz Sobczak get_64bit_val(buf, buf_idx, &temp); 3039*cdcd52d4SBartosz Sobczak obj_info[rsrc_idx].max_cnt = (u32)temp; 3040*cdcd52d4SBartosz Sobczak size = (u32)RS_64_1(temp, 32); 3041*cdcd52d4SBartosz Sobczak obj_info[rsrc_idx].size = LS_64_1(1, size); 3042*cdcd52d4SBartosz Sobczak 3043*cdcd52d4SBartosz Sobczak return temp; 3044*cdcd52d4SBartosz Sobczak } 3045*cdcd52d4SBartosz Sobczak 3046*cdcd52d4SBartosz Sobczak /** 3047*cdcd52d4SBartosz Sobczak * irdma_sc_parse_fpm_query_buf() - parses fpm query buffer 3048*cdcd52d4SBartosz Sobczak * @dev: ptr to shared code device 3049*cdcd52d4SBartosz Sobczak * @buf: ptr to fpm query buffer 3050*cdcd52d4SBartosz Sobczak * @hmc_info: ptr to irdma_hmc_obj_info struct 3051*cdcd52d4SBartosz Sobczak * @hmc_fpm_misc: ptr to fpm data 3052*cdcd52d4SBartosz Sobczak * 3053*cdcd52d4SBartosz Sobczak * parses fpm query buffer and copy max_cnt and 3054*cdcd52d4SBartosz Sobczak * size value of hmc objects in hmc_info 3055*cdcd52d4SBartosz Sobczak */ 3056*cdcd52d4SBartosz Sobczak static int 3057*cdcd52d4SBartosz Sobczak irdma_sc_parse_fpm_query_buf(struct irdma_sc_dev *dev, __le64 * buf, 3058*cdcd52d4SBartosz Sobczak struct irdma_hmc_info *hmc_info, 3059*cdcd52d4SBartosz Sobczak struct irdma_hmc_fpm_misc *hmc_fpm_misc) 3060*cdcd52d4SBartosz Sobczak { 3061*cdcd52d4SBartosz Sobczak struct irdma_hmc_obj_info *obj_info; 3062*cdcd52d4SBartosz Sobczak u64 temp; 3063*cdcd52d4SBartosz Sobczak u32 size; 3064*cdcd52d4SBartosz Sobczak u16 max_pe_sds; 3065*cdcd52d4SBartosz Sobczak 3066*cdcd52d4SBartosz Sobczak obj_info = hmc_info->hmc_obj; 3067*cdcd52d4SBartosz Sobczak 3068*cdcd52d4SBartosz Sobczak get_64bit_val(buf, IRDMA_BYTE_0, &temp); 3069*cdcd52d4SBartosz Sobczak hmc_info->first_sd_index = (u16)RS_64(temp, IRDMA_QUERY_FPM_FIRST_PE_SD_INDEX); 3070*cdcd52d4SBartosz Sobczak max_pe_sds = (u16)RS_64(temp, IRDMA_QUERY_FPM_MAX_PE_SDS); 3071*cdcd52d4SBartosz Sobczak 3072*cdcd52d4SBartosz Sobczak hmc_fpm_misc->max_sds = max_pe_sds; 3073*cdcd52d4SBartosz Sobczak hmc_info->sd_table.sd_cnt = max_pe_sds + hmc_info->first_sd_index; 3074*cdcd52d4SBartosz Sobczak get_64bit_val(buf, 8, &temp); 3075*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_QP].max_cnt = (u32)RS_64(temp, IRDMA_QUERY_FPM_MAX_QPS); 3076*cdcd52d4SBartosz Sobczak size = (u32)RS_64_1(temp, 32); 3077*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_QP].size = LS_64_1(1, size); 3078*cdcd52d4SBartosz Sobczak 3079*cdcd52d4SBartosz Sobczak get_64bit_val(buf, 16, &temp); 3080*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_CQ].max_cnt = (u32)RS_64(temp, IRDMA_QUERY_FPM_MAX_CQS); 3081*cdcd52d4SBartosz Sobczak size = (u32)RS_64_1(temp, 32); 3082*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_CQ].size = LS_64_1(1, size); 3083*cdcd52d4SBartosz Sobczak 3084*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_query(buf, 32, obj_info, IRDMA_HMC_IW_HTE); 3085*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_query(buf, 40, obj_info, IRDMA_HMC_IW_ARP); 3086*cdcd52d4SBartosz Sobczak 3087*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_APBVT_ENTRY].size = 8192; 3088*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_APBVT_ENTRY].max_cnt = 1; 3089*cdcd52d4SBartosz Sobczak 3090*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_query(buf, 48, obj_info, IRDMA_HMC_IW_MR); 3091*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_query(buf, 56, obj_info, IRDMA_HMC_IW_XF); 3092*cdcd52d4SBartosz Sobczak 3093*cdcd52d4SBartosz Sobczak get_64bit_val(buf, 64, &temp); 3094*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_XFFL].max_cnt = (u32)temp; 3095*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_XFFL].size = 4; 3096*cdcd52d4SBartosz Sobczak hmc_fpm_misc->xf_block_size = RS_64(temp, IRDMA_QUERY_FPM_XFBLOCKSIZE); 3097*cdcd52d4SBartosz Sobczak if (!hmc_fpm_misc->xf_block_size) 3098*cdcd52d4SBartosz Sobczak return -EINVAL; 3099*cdcd52d4SBartosz Sobczak 3100*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_query(buf, 72, obj_info, IRDMA_HMC_IW_Q1); 3101*cdcd52d4SBartosz Sobczak get_64bit_val(buf, 80, &temp); 3102*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_Q1FL].max_cnt = (u32)temp; 3103*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_Q1FL].size = 4; 3104*cdcd52d4SBartosz Sobczak 3105*cdcd52d4SBartosz Sobczak hmc_fpm_misc->q1_block_size = RS_64(temp, IRDMA_QUERY_FPM_Q1BLOCKSIZE); 3106*cdcd52d4SBartosz Sobczak if (!hmc_fpm_misc->q1_block_size) 3107*cdcd52d4SBartosz Sobczak return -EINVAL; 3108*cdcd52d4SBartosz Sobczak 3109*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_query(buf, 88, obj_info, IRDMA_HMC_IW_TIMER); 3110*cdcd52d4SBartosz Sobczak 3111*cdcd52d4SBartosz Sobczak get_64bit_val(buf, 112, &temp); 3112*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_PBLE].max_cnt = (u32)temp; 3113*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_PBLE].size = 8; 3114*cdcd52d4SBartosz Sobczak 3115*cdcd52d4SBartosz Sobczak get_64bit_val(buf, 120, &temp); 3116*cdcd52d4SBartosz Sobczak hmc_fpm_misc->max_ceqs = RS_64(temp, IRDMA_QUERY_FPM_MAX_CEQS); 3117*cdcd52d4SBartosz Sobczak hmc_fpm_misc->ht_multiplier = RS_64(temp, IRDMA_QUERY_FPM_HTMULTIPLIER); 3118*cdcd52d4SBartosz Sobczak hmc_fpm_misc->timer_bucket = RS_64(temp, IRDMA_QUERY_FPM_TIMERBUCKET); 3119*cdcd52d4SBartosz Sobczak if (dev->hw_attrs.uk_attrs.hw_rev == IRDMA_GEN_1) 3120*cdcd52d4SBartosz Sobczak return 0; 3121*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_query(buf, 96, obj_info, IRDMA_HMC_IW_FSIMC); 3122*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_query(buf, 104, obj_info, IRDMA_HMC_IW_FSIAV); 3123*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_query(buf, 128, obj_info, IRDMA_HMC_IW_RRF); 3124*cdcd52d4SBartosz Sobczak 3125*cdcd52d4SBartosz Sobczak get_64bit_val(buf, IRDMA_BYTE_136, &temp); 3126*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_RRFFL].max_cnt = (u32)temp; 3127*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_RRFFL].size = 4; 3128*cdcd52d4SBartosz Sobczak hmc_fpm_misc->rrf_block_size = RS_64(temp, IRDMA_QUERY_FPM_RRFBLOCKSIZE); 3129*cdcd52d4SBartosz Sobczak if (!hmc_fpm_misc->rrf_block_size && 3130*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_RRFFL].max_cnt) 3131*cdcd52d4SBartosz Sobczak return -EINVAL; 3132*cdcd52d4SBartosz Sobczak 3133*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_query(buf, 144, obj_info, IRDMA_HMC_IW_HDR); 3134*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_query(buf, 152, obj_info, IRDMA_HMC_IW_MD); 3135*cdcd52d4SBartosz Sobczak irdma_sc_decode_fpm_query(buf, 160, obj_info, IRDMA_HMC_IW_OOISC); 3136*cdcd52d4SBartosz Sobczak 3137*cdcd52d4SBartosz Sobczak get_64bit_val(buf, IRDMA_BYTE_168, &temp); 3138*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_OOISCFFL].max_cnt = (u32)temp; 3139*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_OOISCFFL].size = 4; 3140*cdcd52d4SBartosz Sobczak hmc_fpm_misc->ooiscf_block_size = RS_64(temp, IRDMA_QUERY_FPM_OOISCFBLOCKSIZE); 3141*cdcd52d4SBartosz Sobczak if (!hmc_fpm_misc->ooiscf_block_size && 3142*cdcd52d4SBartosz Sobczak obj_info[IRDMA_HMC_IW_OOISCFFL].max_cnt) 3143*cdcd52d4SBartosz Sobczak return -EINVAL; 3144*cdcd52d4SBartosz Sobczak 3145*cdcd52d4SBartosz Sobczak return 0; 3146*cdcd52d4SBartosz Sobczak } 3147*cdcd52d4SBartosz Sobczak 3148*cdcd52d4SBartosz Sobczak /** 3149*cdcd52d4SBartosz Sobczak * irdma_sc_find_reg_cq - find cq ctx index 3150*cdcd52d4SBartosz Sobczak * @ceq: ceq sc structure 3151*cdcd52d4SBartosz Sobczak * @cq: cq sc structure 3152*cdcd52d4SBartosz Sobczak */ 3153*cdcd52d4SBartosz Sobczak static u32 irdma_sc_find_reg_cq(struct irdma_sc_ceq *ceq, 3154*cdcd52d4SBartosz Sobczak struct irdma_sc_cq *cq){ 3155*cdcd52d4SBartosz Sobczak u32 i; 3156*cdcd52d4SBartosz Sobczak 3157*cdcd52d4SBartosz Sobczak for (i = 0; i < ceq->reg_cq_size; i++) { 3158*cdcd52d4SBartosz Sobczak if (cq == ceq->reg_cq[i]) 3159*cdcd52d4SBartosz Sobczak return i; 3160*cdcd52d4SBartosz Sobczak } 3161*cdcd52d4SBartosz Sobczak 3162*cdcd52d4SBartosz Sobczak return IRDMA_INVALID_CQ_IDX; 3163*cdcd52d4SBartosz Sobczak } 3164*cdcd52d4SBartosz Sobczak 3165*cdcd52d4SBartosz Sobczak /** 3166*cdcd52d4SBartosz Sobczak * irdma_sc_add_cq_ctx - add cq ctx tracking for ceq 3167*cdcd52d4SBartosz Sobczak * @ceq: ceq sc structure 3168*cdcd52d4SBartosz Sobczak * @cq: cq sc structure 3169*cdcd52d4SBartosz Sobczak */ 3170*cdcd52d4SBartosz Sobczak int 3171*cdcd52d4SBartosz Sobczak irdma_sc_add_cq_ctx(struct irdma_sc_ceq *ceq, struct irdma_sc_cq *cq) 3172*cdcd52d4SBartosz Sobczak { 3173*cdcd52d4SBartosz Sobczak unsigned long flags; 3174*cdcd52d4SBartosz Sobczak 3175*cdcd52d4SBartosz Sobczak spin_lock_irqsave(&ceq->req_cq_lock, flags); 3176*cdcd52d4SBartosz Sobczak 3177*cdcd52d4SBartosz Sobczak if (ceq->reg_cq_size == ceq->elem_cnt) { 3178*cdcd52d4SBartosz Sobczak spin_unlock_irqrestore(&ceq->req_cq_lock, flags); 3179*cdcd52d4SBartosz Sobczak return -ENOSPC; 3180*cdcd52d4SBartosz Sobczak } 3181*cdcd52d4SBartosz Sobczak 3182*cdcd52d4SBartosz Sobczak ceq->reg_cq[ceq->reg_cq_size++] = cq; 3183*cdcd52d4SBartosz Sobczak 3184*cdcd52d4SBartosz Sobczak spin_unlock_irqrestore(&ceq->req_cq_lock, flags); 3185*cdcd52d4SBartosz Sobczak 3186*cdcd52d4SBartosz Sobczak return 0; 3187*cdcd52d4SBartosz Sobczak } 3188*cdcd52d4SBartosz Sobczak 3189*cdcd52d4SBartosz Sobczak /** 3190*cdcd52d4SBartosz Sobczak * irdma_sc_remove_cq_ctx - remove cq ctx tracking for ceq 3191*cdcd52d4SBartosz Sobczak * @ceq: ceq sc structure 3192*cdcd52d4SBartosz Sobczak * @cq: cq sc structure 3193*cdcd52d4SBartosz Sobczak */ 3194*cdcd52d4SBartosz Sobczak void 3195*cdcd52d4SBartosz Sobczak irdma_sc_remove_cq_ctx(struct irdma_sc_ceq *ceq, struct irdma_sc_cq *cq) 3196*cdcd52d4SBartosz Sobczak { 3197*cdcd52d4SBartosz Sobczak unsigned long flags; 3198*cdcd52d4SBartosz Sobczak u32 cq_ctx_idx; 3199*cdcd52d4SBartosz Sobczak 3200*cdcd52d4SBartosz Sobczak spin_lock_irqsave(&ceq->req_cq_lock, flags); 3201*cdcd52d4SBartosz Sobczak cq_ctx_idx = irdma_sc_find_reg_cq(ceq, cq); 3202*cdcd52d4SBartosz Sobczak if (cq_ctx_idx == IRDMA_INVALID_CQ_IDX) 3203*cdcd52d4SBartosz Sobczak goto exit; 3204*cdcd52d4SBartosz Sobczak 3205*cdcd52d4SBartosz Sobczak ceq->reg_cq_size--; 3206*cdcd52d4SBartosz Sobczak if (cq_ctx_idx != ceq->reg_cq_size) 3207*cdcd52d4SBartosz Sobczak ceq->reg_cq[cq_ctx_idx] = ceq->reg_cq[ceq->reg_cq_size]; 3208*cdcd52d4SBartosz Sobczak ceq->reg_cq[ceq->reg_cq_size] = NULL; 3209*cdcd52d4SBartosz Sobczak 3210*cdcd52d4SBartosz Sobczak exit: 3211*cdcd52d4SBartosz Sobczak spin_unlock_irqrestore(&ceq->req_cq_lock, flags); 3212*cdcd52d4SBartosz Sobczak } 3213*cdcd52d4SBartosz Sobczak 3214*cdcd52d4SBartosz Sobczak /** 3215*cdcd52d4SBartosz Sobczak * irdma_sc_cqp_init - Initialize buffers for a control Queue Pair 3216*cdcd52d4SBartosz Sobczak * @cqp: IWARP control queue pair pointer 3217*cdcd52d4SBartosz Sobczak * @info: IWARP control queue pair init info pointer 3218*cdcd52d4SBartosz Sobczak * 3219*cdcd52d4SBartosz Sobczak * Initializes the object and context buffers for a control Queue Pair. 3220*cdcd52d4SBartosz Sobczak */ 3221*cdcd52d4SBartosz Sobczak int 3222*cdcd52d4SBartosz Sobczak irdma_sc_cqp_init(struct irdma_sc_cqp *cqp, 3223*cdcd52d4SBartosz Sobczak struct irdma_cqp_init_info *info) 3224*cdcd52d4SBartosz Sobczak { 3225*cdcd52d4SBartosz Sobczak u8 hw_sq_size; 3226*cdcd52d4SBartosz Sobczak 3227*cdcd52d4SBartosz Sobczak if (info->sq_size > IRDMA_CQP_SW_SQSIZE_2048 || 3228*cdcd52d4SBartosz Sobczak info->sq_size < IRDMA_CQP_SW_SQSIZE_4 || 3229*cdcd52d4SBartosz Sobczak ((info->sq_size & (info->sq_size - 1)))) 3230*cdcd52d4SBartosz Sobczak return -EINVAL; 3231*cdcd52d4SBartosz Sobczak 3232*cdcd52d4SBartosz Sobczak hw_sq_size = irdma_get_encoded_wqe_size(info->sq_size, 3233*cdcd52d4SBartosz Sobczak IRDMA_QUEUE_TYPE_CQP); 3234*cdcd52d4SBartosz Sobczak cqp->size = sizeof(*cqp); 3235*cdcd52d4SBartosz Sobczak cqp->sq_size = info->sq_size; 3236*cdcd52d4SBartosz Sobczak cqp->hw_sq_size = hw_sq_size; 3237*cdcd52d4SBartosz Sobczak cqp->sq_base = info->sq; 3238*cdcd52d4SBartosz Sobczak cqp->host_ctx = info->host_ctx; 3239*cdcd52d4SBartosz Sobczak cqp->sq_pa = info->sq_pa; 3240*cdcd52d4SBartosz Sobczak cqp->host_ctx_pa = info->host_ctx_pa; 3241*cdcd52d4SBartosz Sobczak cqp->dev = info->dev; 3242*cdcd52d4SBartosz Sobczak cqp->struct_ver = info->struct_ver; 3243*cdcd52d4SBartosz Sobczak cqp->hw_maj_ver = info->hw_maj_ver; 3244*cdcd52d4SBartosz Sobczak cqp->hw_min_ver = info->hw_min_ver; 3245*cdcd52d4SBartosz Sobczak cqp->scratch_array = info->scratch_array; 3246*cdcd52d4SBartosz Sobczak cqp->polarity = 0; 3247*cdcd52d4SBartosz Sobczak cqp->en_datacenter_tcp = info->en_datacenter_tcp; 3248*cdcd52d4SBartosz Sobczak cqp->ena_vf_count = info->ena_vf_count; 3249*cdcd52d4SBartosz Sobczak cqp->hmc_profile = info->hmc_profile; 3250*cdcd52d4SBartosz Sobczak cqp->ceqs_per_vf = info->ceqs_per_vf; 3251*cdcd52d4SBartosz Sobczak cqp->disable_packed = info->disable_packed; 3252*cdcd52d4SBartosz Sobczak cqp->rocev2_rto_policy = info->rocev2_rto_policy; 3253*cdcd52d4SBartosz Sobczak cqp->protocol_used = info->protocol_used; 3254*cdcd52d4SBartosz Sobczak irdma_memcpy(&cqp->dcqcn_params, &info->dcqcn_params, sizeof(cqp->dcqcn_params)); 3255*cdcd52d4SBartosz Sobczak cqp->en_rem_endpoint_trk = info->en_rem_endpoint_trk; 3256*cdcd52d4SBartosz Sobczak info->dev->cqp = cqp; 3257*cdcd52d4SBartosz Sobczak 3258*cdcd52d4SBartosz Sobczak IRDMA_RING_INIT(cqp->sq_ring, cqp->sq_size); 3259*cdcd52d4SBartosz Sobczak cqp->dev->cqp_cmd_stats[IRDMA_OP_REQ_CMDS] = 0; 3260*cdcd52d4SBartosz Sobczak cqp->dev->cqp_cmd_stats[IRDMA_OP_CMPL_CMDS] = 0; 3261*cdcd52d4SBartosz Sobczak /* for the cqp commands backlog. */ 3262*cdcd52d4SBartosz Sobczak INIT_LIST_HEAD(&cqp->dev->cqp_cmd_head); 3263*cdcd52d4SBartosz Sobczak 3264*cdcd52d4SBartosz Sobczak writel(0, cqp->dev->hw_regs[IRDMA_CQPTAIL]); 3265*cdcd52d4SBartosz Sobczak writel(0, cqp->dev->hw_regs[IRDMA_CQPDB]); 3266*cdcd52d4SBartosz Sobczak writel(0, cqp->dev->hw_regs[IRDMA_CCQPSTATUS]); 3267*cdcd52d4SBartosz Sobczak 3268*cdcd52d4SBartosz Sobczak irdma_debug(cqp->dev, IRDMA_DEBUG_WQE, 3269*cdcd52d4SBartosz Sobczak "sq_size[%04d] hw_sq_size[%04d] sq_base[%p] sq_pa[%llxh] cqp[%p] polarity[x%04x]\n", 3270*cdcd52d4SBartosz Sobczak cqp->sq_size, cqp->hw_sq_size, cqp->sq_base, (unsigned long long)cqp->sq_pa, cqp, 3271*cdcd52d4SBartosz Sobczak cqp->polarity); 3272*cdcd52d4SBartosz Sobczak return 0; 3273*cdcd52d4SBartosz Sobczak } 3274*cdcd52d4SBartosz Sobczak 3275*cdcd52d4SBartosz Sobczak /** 3276*cdcd52d4SBartosz Sobczak * irdma_sc_cqp_create - create cqp during bringup 3277*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 3278*cdcd52d4SBartosz Sobczak * @maj_err: If error, major err number 3279*cdcd52d4SBartosz Sobczak * @min_err: If error, minor err number 3280*cdcd52d4SBartosz Sobczak */ 3281*cdcd52d4SBartosz Sobczak int 3282*cdcd52d4SBartosz Sobczak irdma_sc_cqp_create(struct irdma_sc_cqp *cqp, u16 *maj_err, u16 *min_err) 3283*cdcd52d4SBartosz Sobczak { 3284*cdcd52d4SBartosz Sobczak u64 temp; 3285*cdcd52d4SBartosz Sobczak u8 hw_rev; 3286*cdcd52d4SBartosz Sobczak u32 cnt = 0, p1, p2, val = 0, err_code; 3287*cdcd52d4SBartosz Sobczak int ret_code; 3288*cdcd52d4SBartosz Sobczak 3289*cdcd52d4SBartosz Sobczak hw_rev = cqp->dev->hw_attrs.uk_attrs.hw_rev; 3290*cdcd52d4SBartosz Sobczak cqp->sdbuf.size = IRDMA_UPDATE_SD_BUFF_SIZE * cqp->sq_size; 3291*cdcd52d4SBartosz Sobczak cqp->sdbuf.va = irdma_allocate_dma_mem(cqp->dev->hw, &cqp->sdbuf, 3292*cdcd52d4SBartosz Sobczak cqp->sdbuf.size, 3293*cdcd52d4SBartosz Sobczak IRDMA_SD_BUF_ALIGNMENT); 3294*cdcd52d4SBartosz Sobczak if (!cqp->sdbuf.va) 3295*cdcd52d4SBartosz Sobczak return -ENOMEM; 3296*cdcd52d4SBartosz Sobczak 3297*cdcd52d4SBartosz Sobczak spin_lock_init(&cqp->dev->cqp_lock); 3298*cdcd52d4SBartosz Sobczak 3299*cdcd52d4SBartosz Sobczak temp = LS_64(cqp->hw_sq_size, IRDMA_CQPHC_SQSIZE) | 3300*cdcd52d4SBartosz Sobczak LS_64(cqp->struct_ver, IRDMA_CQPHC_SVER) | 3301*cdcd52d4SBartosz Sobczak LS_64(cqp->disable_packed, IRDMA_CQPHC_DISABLE_PFPDUS) | 3302*cdcd52d4SBartosz Sobczak LS_64(cqp->ceqs_per_vf, IRDMA_CQPHC_CEQPERVF); 3303*cdcd52d4SBartosz Sobczak if (hw_rev >= IRDMA_GEN_2) { 3304*cdcd52d4SBartosz Sobczak temp |= LS_64(cqp->rocev2_rto_policy, IRDMA_CQPHC_ROCEV2_RTO_POLICY) | 3305*cdcd52d4SBartosz Sobczak LS_64(cqp->protocol_used, IRDMA_CQPHC_PROTOCOL_USED); 3306*cdcd52d4SBartosz Sobczak } 3307*cdcd52d4SBartosz Sobczak 3308*cdcd52d4SBartosz Sobczak set_64bit_val(cqp->host_ctx, IRDMA_BYTE_0, temp); 3309*cdcd52d4SBartosz Sobczak set_64bit_val(cqp->host_ctx, IRDMA_BYTE_8, cqp->sq_pa); 3310*cdcd52d4SBartosz Sobczak 3311*cdcd52d4SBartosz Sobczak temp = LS_64(cqp->ena_vf_count, IRDMA_CQPHC_ENABLED_VFS) | 3312*cdcd52d4SBartosz Sobczak LS_64(cqp->hmc_profile, IRDMA_CQPHC_HMC_PROFILE); 3313*cdcd52d4SBartosz Sobczak if (hw_rev >= IRDMA_GEN_2) 3314*cdcd52d4SBartosz Sobczak temp |= LS_64(cqp->en_rem_endpoint_trk, IRDMA_CQPHC_EN_REM_ENDPOINT_TRK); 3315*cdcd52d4SBartosz Sobczak set_64bit_val(cqp->host_ctx, IRDMA_BYTE_16, temp); 3316*cdcd52d4SBartosz Sobczak set_64bit_val(cqp->host_ctx, IRDMA_BYTE_24, (uintptr_t)cqp); 3317*cdcd52d4SBartosz Sobczak temp = LS_64(cqp->hw_maj_ver, IRDMA_CQPHC_HW_MAJVER) | 3318*cdcd52d4SBartosz Sobczak LS_64(cqp->hw_min_ver, IRDMA_CQPHC_HW_MINVER); 3319*cdcd52d4SBartosz Sobczak if (hw_rev >= IRDMA_GEN_2) { 3320*cdcd52d4SBartosz Sobczak temp |= LS_64(cqp->dcqcn_params.min_rate, IRDMA_CQPHC_MIN_RATE) | 3321*cdcd52d4SBartosz Sobczak LS_64(cqp->dcqcn_params.min_dec_factor, IRDMA_CQPHC_MIN_DEC_FACTOR); 3322*cdcd52d4SBartosz Sobczak } 3323*cdcd52d4SBartosz Sobczak set_64bit_val(cqp->host_ctx, IRDMA_BYTE_32, temp); 3324*cdcd52d4SBartosz Sobczak set_64bit_val(cqp->host_ctx, IRDMA_BYTE_40, 0); 3325*cdcd52d4SBartosz Sobczak temp = 0; 3326*cdcd52d4SBartosz Sobczak if (hw_rev >= IRDMA_GEN_2) { 3327*cdcd52d4SBartosz Sobczak temp |= LS_64(cqp->dcqcn_params.dcqcn_t, IRDMA_CQPHC_DCQCN_T) | 3328*cdcd52d4SBartosz Sobczak LS_64(cqp->dcqcn_params.rai_factor, IRDMA_CQPHC_RAI_FACTOR) | 3329*cdcd52d4SBartosz Sobczak LS_64(cqp->dcqcn_params.hai_factor, IRDMA_CQPHC_HAI_FACTOR); 3330*cdcd52d4SBartosz Sobczak } 3331*cdcd52d4SBartosz Sobczak set_64bit_val(cqp->host_ctx, IRDMA_BYTE_48, temp); 3332*cdcd52d4SBartosz Sobczak temp = 0; 3333*cdcd52d4SBartosz Sobczak if (hw_rev >= IRDMA_GEN_2) { 3334*cdcd52d4SBartosz Sobczak temp |= LS_64(cqp->dcqcn_params.dcqcn_b, IRDMA_CQPHC_DCQCN_B) | 3335*cdcd52d4SBartosz Sobczak LS_64(cqp->dcqcn_params.dcqcn_f, IRDMA_CQPHC_DCQCN_F) | 3336*cdcd52d4SBartosz Sobczak LS_64(cqp->dcqcn_params.cc_cfg_valid, IRDMA_CQPHC_CC_CFG_VALID) | 3337*cdcd52d4SBartosz Sobczak LS_64(cqp->dcqcn_params.rreduce_mperiod, IRDMA_CQPHC_RREDUCE_MPERIOD); 3338*cdcd52d4SBartosz Sobczak } 3339*cdcd52d4SBartosz Sobczak set_64bit_val(cqp->host_ctx, IRDMA_BYTE_56, temp); 3340*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "CQP_HOST_CTX WQE", 3341*cdcd52d4SBartosz Sobczak cqp->host_ctx, IRDMA_CQP_CTX_SIZE * 8); 3342*cdcd52d4SBartosz Sobczak p1 = RS_32_1(cqp->host_ctx_pa, 32); 3343*cdcd52d4SBartosz Sobczak p2 = (u32)cqp->host_ctx_pa; 3344*cdcd52d4SBartosz Sobczak 3345*cdcd52d4SBartosz Sobczak writel(p1, cqp->dev->hw_regs[IRDMA_CCQPHIGH]); 3346*cdcd52d4SBartosz Sobczak writel(p2, cqp->dev->hw_regs[IRDMA_CCQPLOW]); 3347*cdcd52d4SBartosz Sobczak 3348*cdcd52d4SBartosz Sobczak do { 3349*cdcd52d4SBartosz Sobczak if (cnt++ > cqp->dev->hw_attrs.max_done_count) { 3350*cdcd52d4SBartosz Sobczak ret_code = -ETIMEDOUT; 3351*cdcd52d4SBartosz Sobczak goto err; 3352*cdcd52d4SBartosz Sobczak } 3353*cdcd52d4SBartosz Sobczak irdma_usec_delay(cqp->dev->hw_attrs.max_sleep_count); 3354*cdcd52d4SBartosz Sobczak val = readl(cqp->dev->hw_regs[IRDMA_CCQPSTATUS]); 3355*cdcd52d4SBartosz Sobczak } while (!val); 3356*cdcd52d4SBartosz Sobczak 3357*cdcd52d4SBartosz Sobczak if (FLD_RS_32(cqp->dev, val, IRDMA_CCQPSTATUS_CCQP_ERR)) { 3358*cdcd52d4SBartosz Sobczak ret_code = -EOPNOTSUPP; 3359*cdcd52d4SBartosz Sobczak goto err; 3360*cdcd52d4SBartosz Sobczak } 3361*cdcd52d4SBartosz Sobczak 3362*cdcd52d4SBartosz Sobczak cqp->process_cqp_sds = irdma_update_sds_noccq; 3363*cdcd52d4SBartosz Sobczak return 0; 3364*cdcd52d4SBartosz Sobczak 3365*cdcd52d4SBartosz Sobczak err: 3366*cdcd52d4SBartosz Sobczak spin_lock_destroy(&cqp->dev->cqp_lock); 3367*cdcd52d4SBartosz Sobczak irdma_free_dma_mem(cqp->dev->hw, &cqp->sdbuf); 3368*cdcd52d4SBartosz Sobczak err_code = readl(cqp->dev->hw_regs[IRDMA_CQPERRCODES]); 3369*cdcd52d4SBartosz Sobczak *min_err = RS_32(err_code, IRDMA_CQPERRCODES_CQP_MINOR_CODE); 3370*cdcd52d4SBartosz Sobczak *maj_err = RS_32(err_code, IRDMA_CQPERRCODES_CQP_MAJOR_CODE); 3371*cdcd52d4SBartosz Sobczak return ret_code; 3372*cdcd52d4SBartosz Sobczak } 3373*cdcd52d4SBartosz Sobczak 3374*cdcd52d4SBartosz Sobczak /** 3375*cdcd52d4SBartosz Sobczak * irdma_sc_cqp_post_sq - post of cqp's sq 3376*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 3377*cdcd52d4SBartosz Sobczak */ 3378*cdcd52d4SBartosz Sobczak void 3379*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(struct irdma_sc_cqp *cqp) 3380*cdcd52d4SBartosz Sobczak { 3381*cdcd52d4SBartosz Sobczak db_wr32(IRDMA_RING_CURRENT_HEAD(cqp->sq_ring), cqp->dev->cqp_db); 3382*cdcd52d4SBartosz Sobczak 3383*cdcd52d4SBartosz Sobczak irdma_debug(cqp->dev, IRDMA_DEBUG_WQE, 3384*cdcd52d4SBartosz Sobczak "CQP SQ head 0x%x tail 0x%x size 0x%x\n", cqp->sq_ring.head, 3385*cdcd52d4SBartosz Sobczak cqp->sq_ring.tail, cqp->sq_ring.size); 3386*cdcd52d4SBartosz Sobczak } 3387*cdcd52d4SBartosz Sobczak 3388*cdcd52d4SBartosz Sobczak /** 3389*cdcd52d4SBartosz Sobczak * irdma_sc_cqp_get_next_send_wqe_idx - get next wqe on cqp sq 3390*cdcd52d4SBartosz Sobczak * and pass back index 3391*cdcd52d4SBartosz Sobczak * @cqp: CQP HW structure 3392*cdcd52d4SBartosz Sobczak * @scratch: private data for CQP WQE 3393*cdcd52d4SBartosz Sobczak * @wqe_idx: WQE index of CQP SQ 3394*cdcd52d4SBartosz Sobczak */ 3395*cdcd52d4SBartosz Sobczak __le64 * 3396*cdcd52d4SBartosz Sobczak irdma_sc_cqp_get_next_send_wqe_idx(struct irdma_sc_cqp *cqp, u64 scratch, 3397*cdcd52d4SBartosz Sobczak u32 *wqe_idx) 3398*cdcd52d4SBartosz Sobczak { 3399*cdcd52d4SBartosz Sobczak __le64 *wqe = NULL; 3400*cdcd52d4SBartosz Sobczak int ret_code; 3401*cdcd52d4SBartosz Sobczak 3402*cdcd52d4SBartosz Sobczak if (IRDMA_RING_FULL_ERR(cqp->sq_ring)) { 3403*cdcd52d4SBartosz Sobczak irdma_debug(cqp->dev, IRDMA_DEBUG_WQE, 3404*cdcd52d4SBartosz Sobczak "CQP SQ is full, head 0x%x tail 0x%x size 0x%x\n", 3405*cdcd52d4SBartosz Sobczak cqp->sq_ring.head, cqp->sq_ring.tail, 3406*cdcd52d4SBartosz Sobczak cqp->sq_ring.size); 3407*cdcd52d4SBartosz Sobczak return NULL; 3408*cdcd52d4SBartosz Sobczak } 3409*cdcd52d4SBartosz Sobczak IRDMA_ATOMIC_RING_MOVE_HEAD(cqp->sq_ring, *wqe_idx, ret_code); 3410*cdcd52d4SBartosz Sobczak if (ret_code) 3411*cdcd52d4SBartosz Sobczak return NULL; 3412*cdcd52d4SBartosz Sobczak 3413*cdcd52d4SBartosz Sobczak cqp->dev->cqp_cmd_stats[IRDMA_OP_REQ_CMDS]++; 3414*cdcd52d4SBartosz Sobczak if (!*wqe_idx) 3415*cdcd52d4SBartosz Sobczak cqp->polarity = !cqp->polarity; 3416*cdcd52d4SBartosz Sobczak wqe = cqp->sq_base[*wqe_idx].elem; 3417*cdcd52d4SBartosz Sobczak cqp->scratch_array[*wqe_idx] = scratch; 3418*cdcd52d4SBartosz Sobczak 3419*cdcd52d4SBartosz Sobczak memset(&wqe[0], 0, 24); 3420*cdcd52d4SBartosz Sobczak memset(&wqe[4], 0, 32); 3421*cdcd52d4SBartosz Sobczak 3422*cdcd52d4SBartosz Sobczak return wqe; 3423*cdcd52d4SBartosz Sobczak } 3424*cdcd52d4SBartosz Sobczak 3425*cdcd52d4SBartosz Sobczak /** 3426*cdcd52d4SBartosz Sobczak * irdma_sc_cqp_destroy - destroy cqp during close 3427*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 3428*cdcd52d4SBartosz Sobczak */ 3429*cdcd52d4SBartosz Sobczak int 3430*cdcd52d4SBartosz Sobczak irdma_sc_cqp_destroy(struct irdma_sc_cqp *cqp) 3431*cdcd52d4SBartosz Sobczak { 3432*cdcd52d4SBartosz Sobczak u32 cnt = 0, val; 3433*cdcd52d4SBartosz Sobczak int ret_code = 0; 3434*cdcd52d4SBartosz Sobczak 3435*cdcd52d4SBartosz Sobczak writel(0, cqp->dev->hw_regs[IRDMA_CCQPHIGH]); 3436*cdcd52d4SBartosz Sobczak writel(0, cqp->dev->hw_regs[IRDMA_CCQPLOW]); 3437*cdcd52d4SBartosz Sobczak do { 3438*cdcd52d4SBartosz Sobczak if (cnt++ > cqp->dev->hw_attrs.max_done_count) { 3439*cdcd52d4SBartosz Sobczak ret_code = -ETIMEDOUT; 3440*cdcd52d4SBartosz Sobczak break; 3441*cdcd52d4SBartosz Sobczak } 3442*cdcd52d4SBartosz Sobczak irdma_usec_delay(cqp->dev->hw_attrs.max_sleep_count); 3443*cdcd52d4SBartosz Sobczak val = readl(cqp->dev->hw_regs[IRDMA_CCQPSTATUS]); 3444*cdcd52d4SBartosz Sobczak } while (FLD_RS_32(cqp->dev, val, IRDMA_CCQPSTATUS_CCQP_DONE)); 3445*cdcd52d4SBartosz Sobczak 3446*cdcd52d4SBartosz Sobczak irdma_free_dma_mem(cqp->dev->hw, &cqp->sdbuf); 3447*cdcd52d4SBartosz Sobczak spin_lock_destroy(&cqp->dev->cqp_lock); 3448*cdcd52d4SBartosz Sobczak return ret_code; 3449*cdcd52d4SBartosz Sobczak } 3450*cdcd52d4SBartosz Sobczak 3451*cdcd52d4SBartosz Sobczak /** 3452*cdcd52d4SBartosz Sobczak * irdma_sc_ccq_arm - enable intr for control cq 3453*cdcd52d4SBartosz Sobczak * @ccq: ccq sc struct 3454*cdcd52d4SBartosz Sobczak */ 3455*cdcd52d4SBartosz Sobczak void 3456*cdcd52d4SBartosz Sobczak irdma_sc_ccq_arm(struct irdma_sc_cq *ccq) 3457*cdcd52d4SBartosz Sobczak { 3458*cdcd52d4SBartosz Sobczak u64 temp_val; 3459*cdcd52d4SBartosz Sobczak u16 sw_cq_sel; 3460*cdcd52d4SBartosz Sobczak u8 arm_next_se; 3461*cdcd52d4SBartosz Sobczak u8 arm_seq_num; 3462*cdcd52d4SBartosz Sobczak 3463*cdcd52d4SBartosz Sobczak get_64bit_val(ccq->cq_uk.shadow_area, IRDMA_BYTE_32, &temp_val); 3464*cdcd52d4SBartosz Sobczak sw_cq_sel = (u16)RS_64(temp_val, IRDMA_CQ_DBSA_SW_CQ_SELECT); 3465*cdcd52d4SBartosz Sobczak arm_next_se = (u8)RS_64(temp_val, IRDMA_CQ_DBSA_ARM_NEXT_SE); 3466*cdcd52d4SBartosz Sobczak arm_seq_num = (u8)RS_64(temp_val, IRDMA_CQ_DBSA_ARM_SEQ_NUM); 3467*cdcd52d4SBartosz Sobczak arm_seq_num++; 3468*cdcd52d4SBartosz Sobczak temp_val = LS_64(arm_seq_num, IRDMA_CQ_DBSA_ARM_SEQ_NUM) | 3469*cdcd52d4SBartosz Sobczak LS_64(sw_cq_sel, IRDMA_CQ_DBSA_SW_CQ_SELECT) | 3470*cdcd52d4SBartosz Sobczak LS_64(arm_next_se, IRDMA_CQ_DBSA_ARM_NEXT_SE) | 3471*cdcd52d4SBartosz Sobczak LS_64(1, IRDMA_CQ_DBSA_ARM_NEXT); 3472*cdcd52d4SBartosz Sobczak set_64bit_val(ccq->cq_uk.shadow_area, IRDMA_BYTE_32, temp_val); 3473*cdcd52d4SBartosz Sobczak 3474*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure shadow area is updated before arming */ 3475*cdcd52d4SBartosz Sobczak 3476*cdcd52d4SBartosz Sobczak db_wr32(ccq->cq_uk.cq_id, ccq->dev->cq_arm_db); 3477*cdcd52d4SBartosz Sobczak } 3478*cdcd52d4SBartosz Sobczak 3479*cdcd52d4SBartosz Sobczak /** 3480*cdcd52d4SBartosz Sobczak * irdma_sc_ccq_get_cqe_info - get ccq's cq entry 3481*cdcd52d4SBartosz Sobczak * @ccq: ccq sc struct 3482*cdcd52d4SBartosz Sobczak * @info: completion q entry to return 3483*cdcd52d4SBartosz Sobczak */ 3484*cdcd52d4SBartosz Sobczak int 3485*cdcd52d4SBartosz Sobczak irdma_sc_ccq_get_cqe_info(struct irdma_sc_cq *ccq, 3486*cdcd52d4SBartosz Sobczak struct irdma_ccq_cqe_info *info) 3487*cdcd52d4SBartosz Sobczak { 3488*cdcd52d4SBartosz Sobczak u64 qp_ctx, temp, temp1; 3489*cdcd52d4SBartosz Sobczak __le64 *cqe; 3490*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 3491*cdcd52d4SBartosz Sobczak u32 wqe_idx; 3492*cdcd52d4SBartosz Sobczak u32 error; 3493*cdcd52d4SBartosz Sobczak u8 polarity; 3494*cdcd52d4SBartosz Sobczak int ret_code = 0; 3495*cdcd52d4SBartosz Sobczak 3496*cdcd52d4SBartosz Sobczak if (ccq->cq_uk.avoid_mem_cflct) 3497*cdcd52d4SBartosz Sobczak cqe = IRDMA_GET_CURRENT_EXTENDED_CQ_ELEM(&ccq->cq_uk); 3498*cdcd52d4SBartosz Sobczak else 3499*cdcd52d4SBartosz Sobczak cqe = IRDMA_GET_CURRENT_CQ_ELEM(&ccq->cq_uk); 3500*cdcd52d4SBartosz Sobczak 3501*cdcd52d4SBartosz Sobczak get_64bit_val(cqe, IRDMA_BYTE_24, &temp); 3502*cdcd52d4SBartosz Sobczak polarity = (u8)RS_64(temp, IRDMA_CQ_VALID); 3503*cdcd52d4SBartosz Sobczak if (polarity != ccq->cq_uk.polarity) 3504*cdcd52d4SBartosz Sobczak return -ENOENT; 3505*cdcd52d4SBartosz Sobczak 3506*cdcd52d4SBartosz Sobczak get_64bit_val(cqe, IRDMA_BYTE_8, &qp_ctx); 3507*cdcd52d4SBartosz Sobczak cqp = (struct irdma_sc_cqp *)(irdma_uintptr) qp_ctx; 3508*cdcd52d4SBartosz Sobczak info->error = (bool)RS_64(temp, IRDMA_CQ_ERROR); 3509*cdcd52d4SBartosz Sobczak info->maj_err_code = IRDMA_CQPSQ_MAJ_NO_ERROR; 3510*cdcd52d4SBartosz Sobczak info->min_err_code = (u16)RS_64(temp, IRDMA_CQ_MINERR); 3511*cdcd52d4SBartosz Sobczak if (info->error) { 3512*cdcd52d4SBartosz Sobczak info->maj_err_code = (u16)RS_64(temp, IRDMA_CQ_MAJERR); 3513*cdcd52d4SBartosz Sobczak error = readl(cqp->dev->hw_regs[IRDMA_CQPERRCODES]); 3514*cdcd52d4SBartosz Sobczak irdma_debug(cqp->dev, IRDMA_DEBUG_CQP, 3515*cdcd52d4SBartosz Sobczak "CQPERRCODES error_code[x%08X]\n", error); 3516*cdcd52d4SBartosz Sobczak } 3517*cdcd52d4SBartosz Sobczak 3518*cdcd52d4SBartosz Sobczak wqe_idx = (u32)RS_64(temp, IRDMA_CQ_WQEIDX); 3519*cdcd52d4SBartosz Sobczak info->scratch = cqp->scratch_array[wqe_idx]; 3520*cdcd52d4SBartosz Sobczak 3521*cdcd52d4SBartosz Sobczak get_64bit_val(cqe, IRDMA_BYTE_16, &temp1); 3522*cdcd52d4SBartosz Sobczak info->op_ret_val = (u32)RS_64(temp1, IRDMA_CCQ_OPRETVAL); 3523*cdcd52d4SBartosz Sobczak get_64bit_val(cqp->sq_base[wqe_idx].elem, IRDMA_BYTE_24, &temp1); 3524*cdcd52d4SBartosz Sobczak info->op_code = (u8)RS_64(temp1, IRDMA_CQPSQ_OPCODE); 3525*cdcd52d4SBartosz Sobczak info->cqp = cqp; 3526*cdcd52d4SBartosz Sobczak 3527*cdcd52d4SBartosz Sobczak /* move the head for cq */ 3528*cdcd52d4SBartosz Sobczak IRDMA_RING_MOVE_HEAD(ccq->cq_uk.cq_ring, ret_code); 3529*cdcd52d4SBartosz Sobczak if (!IRDMA_RING_CURRENT_HEAD(ccq->cq_uk.cq_ring)) 3530*cdcd52d4SBartosz Sobczak ccq->cq_uk.polarity ^= 1; 3531*cdcd52d4SBartosz Sobczak 3532*cdcd52d4SBartosz Sobczak /* update cq tail in cq shadow memory also */ 3533*cdcd52d4SBartosz Sobczak IRDMA_RING_MOVE_TAIL(ccq->cq_uk.cq_ring); 3534*cdcd52d4SBartosz Sobczak set_64bit_val(ccq->cq_uk.shadow_area, IRDMA_BYTE_0, 3535*cdcd52d4SBartosz Sobczak IRDMA_RING_CURRENT_HEAD(ccq->cq_uk.cq_ring)); 3536*cdcd52d4SBartosz Sobczak 3537*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure shadow area is updated before moving tail */ 3538*cdcd52d4SBartosz Sobczak 3539*cdcd52d4SBartosz Sobczak IRDMA_RING_MOVE_TAIL(cqp->sq_ring); 3540*cdcd52d4SBartosz Sobczak ccq->dev->cqp_cmd_stats[IRDMA_OP_CMPL_CMDS]++; 3541*cdcd52d4SBartosz Sobczak 3542*cdcd52d4SBartosz Sobczak return ret_code; 3543*cdcd52d4SBartosz Sobczak } 3544*cdcd52d4SBartosz Sobczak 3545*cdcd52d4SBartosz Sobczak /** 3546*cdcd52d4SBartosz Sobczak * irdma_sc_poll_for_cqp_op_done - Waits for last write to complete in CQP SQ 3547*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 3548*cdcd52d4SBartosz Sobczak * @op_code: cqp opcode for completion 3549*cdcd52d4SBartosz Sobczak * @compl_info: completion q entry to return 3550*cdcd52d4SBartosz Sobczak */ 3551*cdcd52d4SBartosz Sobczak int 3552*cdcd52d4SBartosz Sobczak irdma_sc_poll_for_cqp_op_done(struct irdma_sc_cqp *cqp, u8 op_code, 3553*cdcd52d4SBartosz Sobczak struct irdma_ccq_cqe_info *compl_info) 3554*cdcd52d4SBartosz Sobczak { 3555*cdcd52d4SBartosz Sobczak struct irdma_ccq_cqe_info info = {0}; 3556*cdcd52d4SBartosz Sobczak struct irdma_sc_cq *ccq; 3557*cdcd52d4SBartosz Sobczak int ret_code = 0; 3558*cdcd52d4SBartosz Sobczak u32 cnt = 0; 3559*cdcd52d4SBartosz Sobczak 3560*cdcd52d4SBartosz Sobczak ccq = cqp->dev->ccq; 3561*cdcd52d4SBartosz Sobczak while (1) { 3562*cdcd52d4SBartosz Sobczak if (cnt++ > 100 * cqp->dev->hw_attrs.max_done_count) 3563*cdcd52d4SBartosz Sobczak return -ETIMEDOUT; 3564*cdcd52d4SBartosz Sobczak 3565*cdcd52d4SBartosz Sobczak if (cqp->dev->no_cqp) 3566*cdcd52d4SBartosz Sobczak return -ETIMEDOUT; 3567*cdcd52d4SBartosz Sobczak 3568*cdcd52d4SBartosz Sobczak if (irdma_sc_ccq_get_cqe_info(ccq, &info)) { 3569*cdcd52d4SBartosz Sobczak irdma_usec_delay(cqp->dev->hw_attrs.max_sleep_count); 3570*cdcd52d4SBartosz Sobczak continue; 3571*cdcd52d4SBartosz Sobczak } 3572*cdcd52d4SBartosz Sobczak if (info.error && info.op_code != IRDMA_CQP_OP_QUERY_STAG) { 3573*cdcd52d4SBartosz Sobczak ret_code = -EIO; 3574*cdcd52d4SBartosz Sobczak break; 3575*cdcd52d4SBartosz Sobczak } 3576*cdcd52d4SBartosz Sobczak /* make sure op code matches */ 3577*cdcd52d4SBartosz Sobczak if (op_code == info.op_code) 3578*cdcd52d4SBartosz Sobczak break; 3579*cdcd52d4SBartosz Sobczak irdma_debug(cqp->dev, IRDMA_DEBUG_WQE, 3580*cdcd52d4SBartosz Sobczak "opcode mismatch for my op code 0x%x, returned opcode %x\n", 3581*cdcd52d4SBartosz Sobczak op_code, info.op_code); 3582*cdcd52d4SBartosz Sobczak } 3583*cdcd52d4SBartosz Sobczak 3584*cdcd52d4SBartosz Sobczak if (compl_info) 3585*cdcd52d4SBartosz Sobczak irdma_memcpy(compl_info, &info, sizeof(*compl_info)); 3586*cdcd52d4SBartosz Sobczak 3587*cdcd52d4SBartosz Sobczak return ret_code; 3588*cdcd52d4SBartosz Sobczak } 3589*cdcd52d4SBartosz Sobczak 3590*cdcd52d4SBartosz Sobczak /** 3591*cdcd52d4SBartosz Sobczak * irdma_sc_manage_hmc_pm_func_table - manage of function table 3592*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 3593*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 3594*cdcd52d4SBartosz Sobczak * @info: info for the manage function table operation 3595*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 3596*cdcd52d4SBartosz Sobczak */ 3597*cdcd52d4SBartosz Sobczak static int 3598*cdcd52d4SBartosz Sobczak irdma_sc_manage_hmc_pm_func_table(struct irdma_sc_cqp *cqp, 3599*cdcd52d4SBartosz Sobczak struct irdma_hmc_fcn_info *info, 3600*cdcd52d4SBartosz Sobczak u64 scratch, bool post_sq) 3601*cdcd52d4SBartosz Sobczak { 3602*cdcd52d4SBartosz Sobczak __le64 *wqe; 3603*cdcd52d4SBartosz Sobczak u64 hdr; 3604*cdcd52d4SBartosz Sobczak 3605*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 3606*cdcd52d4SBartosz Sobczak if (!wqe) 3607*cdcd52d4SBartosz Sobczak return -ENOSPC; 3608*cdcd52d4SBartosz Sobczak 3609*cdcd52d4SBartosz Sobczak hdr = LS_64(info->vf_id, IRDMA_CQPSQ_MHMC_VFIDX) | 3610*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_MANAGE_HMC_PM_FUNC_TABLE, 3611*cdcd52d4SBartosz Sobczak IRDMA_CQPSQ_OPCODE) | 3612*cdcd52d4SBartosz Sobczak LS_64(info->free_fcn, IRDMA_CQPSQ_MHMC_FREEPMFN) | 3613*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 3614*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 3615*cdcd52d4SBartosz Sobczak 3616*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 3617*cdcd52d4SBartosz Sobczak 3618*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, 3619*cdcd52d4SBartosz Sobczak "MANAGE_HMC_PM_FUNC_TABLE WQE", wqe, 3620*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 3621*cdcd52d4SBartosz Sobczak if (post_sq) 3622*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 3623*cdcd52d4SBartosz Sobczak 3624*cdcd52d4SBartosz Sobczak return 0; 3625*cdcd52d4SBartosz Sobczak } 3626*cdcd52d4SBartosz Sobczak 3627*cdcd52d4SBartosz Sobczak /** 3628*cdcd52d4SBartosz Sobczak * irdma_sc_commit_fpm_val_done - wait for cqp eqe completion 3629*cdcd52d4SBartosz Sobczak * for fpm commit 3630*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 3631*cdcd52d4SBartosz Sobczak */ 3632*cdcd52d4SBartosz Sobczak static int 3633*cdcd52d4SBartosz Sobczak irdma_sc_commit_fpm_val_done(struct irdma_sc_cqp *cqp) 3634*cdcd52d4SBartosz Sobczak { 3635*cdcd52d4SBartosz Sobczak return irdma_sc_poll_for_cqp_op_done(cqp, IRDMA_CQP_OP_COMMIT_FPM_VAL, 3636*cdcd52d4SBartosz Sobczak NULL); 3637*cdcd52d4SBartosz Sobczak } 3638*cdcd52d4SBartosz Sobczak 3639*cdcd52d4SBartosz Sobczak /** 3640*cdcd52d4SBartosz Sobczak * irdma_sc_commit_fpm_val - cqp wqe for commit fpm values 3641*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 3642*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 3643*cdcd52d4SBartosz Sobczak * @hmc_fn_id: hmc function id 3644*cdcd52d4SBartosz Sobczak * @commit_fpm_mem: Memory for fpm values 3645*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 3646*cdcd52d4SBartosz Sobczak * @wait_type: poll ccq or cqp registers for cqp completion 3647*cdcd52d4SBartosz Sobczak */ 3648*cdcd52d4SBartosz Sobczak static int 3649*cdcd52d4SBartosz Sobczak irdma_sc_commit_fpm_val(struct irdma_sc_cqp *cqp, u64 scratch, 3650*cdcd52d4SBartosz Sobczak u8 hmc_fn_id, 3651*cdcd52d4SBartosz Sobczak struct irdma_dma_mem *commit_fpm_mem, 3652*cdcd52d4SBartosz Sobczak bool post_sq, u8 wait_type) 3653*cdcd52d4SBartosz Sobczak { 3654*cdcd52d4SBartosz Sobczak __le64 *wqe; 3655*cdcd52d4SBartosz Sobczak u64 hdr; 3656*cdcd52d4SBartosz Sobczak u32 tail, val, error; 3657*cdcd52d4SBartosz Sobczak int ret_code = 0; 3658*cdcd52d4SBartosz Sobczak 3659*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 3660*cdcd52d4SBartosz Sobczak if (!wqe) 3661*cdcd52d4SBartosz Sobczak return -ENOSPC; 3662*cdcd52d4SBartosz Sobczak 3663*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, hmc_fn_id); 3664*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, commit_fpm_mem->pa); 3665*cdcd52d4SBartosz Sobczak 3666*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMA_COMMIT_FPM_BUF_SIZE, IRDMA_CQPSQ_BUFSIZE) | 3667*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_COMMIT_FPM_VAL, IRDMA_CQPSQ_OPCODE) | 3668*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 3669*cdcd52d4SBartosz Sobczak 3670*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 3671*cdcd52d4SBartosz Sobczak 3672*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 3673*cdcd52d4SBartosz Sobczak 3674*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "COMMIT_FPM_VAL WQE", wqe, 3675*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 3676*cdcd52d4SBartosz Sobczak irdma_get_cqp_reg_info(cqp, &val, &tail, &error); 3677*cdcd52d4SBartosz Sobczak 3678*cdcd52d4SBartosz Sobczak if (post_sq) { 3679*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 3680*cdcd52d4SBartosz Sobczak if (wait_type == IRDMA_CQP_WAIT_POLL_REGS) 3681*cdcd52d4SBartosz Sobczak ret_code = irdma_cqp_poll_registers(cqp, tail, 3682*cdcd52d4SBartosz Sobczak cqp->dev->hw_attrs.max_done_count); 3683*cdcd52d4SBartosz Sobczak else if (wait_type == IRDMA_CQP_WAIT_POLL_CQ) 3684*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_commit_fpm_val_done(cqp); 3685*cdcd52d4SBartosz Sobczak } 3686*cdcd52d4SBartosz Sobczak 3687*cdcd52d4SBartosz Sobczak return ret_code; 3688*cdcd52d4SBartosz Sobczak } 3689*cdcd52d4SBartosz Sobczak 3690*cdcd52d4SBartosz Sobczak /** 3691*cdcd52d4SBartosz Sobczak * irdma_sc_query_fpm_val_done - poll for cqp wqe completion for 3692*cdcd52d4SBartosz Sobczak * query fpm 3693*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 3694*cdcd52d4SBartosz Sobczak */ 3695*cdcd52d4SBartosz Sobczak static int 3696*cdcd52d4SBartosz Sobczak irdma_sc_query_fpm_val_done(struct irdma_sc_cqp *cqp) 3697*cdcd52d4SBartosz Sobczak { 3698*cdcd52d4SBartosz Sobczak return irdma_sc_poll_for_cqp_op_done(cqp, IRDMA_CQP_OP_QUERY_FPM_VAL, 3699*cdcd52d4SBartosz Sobczak NULL); 3700*cdcd52d4SBartosz Sobczak } 3701*cdcd52d4SBartosz Sobczak 3702*cdcd52d4SBartosz Sobczak /** 3703*cdcd52d4SBartosz Sobczak * irdma_sc_query_fpm_val - cqp wqe query fpm values 3704*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 3705*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 3706*cdcd52d4SBartosz Sobczak * @hmc_fn_id: hmc function id 3707*cdcd52d4SBartosz Sobczak * @query_fpm_mem: memory for return fpm values 3708*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 3709*cdcd52d4SBartosz Sobczak * @wait_type: poll ccq or cqp registers for cqp completion 3710*cdcd52d4SBartosz Sobczak */ 3711*cdcd52d4SBartosz Sobczak static int 3712*cdcd52d4SBartosz Sobczak irdma_sc_query_fpm_val(struct irdma_sc_cqp *cqp, u64 scratch, 3713*cdcd52d4SBartosz Sobczak u8 hmc_fn_id, 3714*cdcd52d4SBartosz Sobczak struct irdma_dma_mem *query_fpm_mem, 3715*cdcd52d4SBartosz Sobczak bool post_sq, u8 wait_type) 3716*cdcd52d4SBartosz Sobczak { 3717*cdcd52d4SBartosz Sobczak __le64 *wqe; 3718*cdcd52d4SBartosz Sobczak u64 hdr; 3719*cdcd52d4SBartosz Sobczak u32 tail, val, error; 3720*cdcd52d4SBartosz Sobczak int ret_code = 0; 3721*cdcd52d4SBartosz Sobczak 3722*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 3723*cdcd52d4SBartosz Sobczak if (!wqe) 3724*cdcd52d4SBartosz Sobczak return -ENOSPC; 3725*cdcd52d4SBartosz Sobczak 3726*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, hmc_fn_id); 3727*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, query_fpm_mem->pa); 3728*cdcd52d4SBartosz Sobczak 3729*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMA_CQP_OP_QUERY_FPM_VAL, IRDMA_CQPSQ_OPCODE) | 3730*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 3731*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 3732*cdcd52d4SBartosz Sobczak 3733*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 3734*cdcd52d4SBartosz Sobczak 3735*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "QUERY_FPM WQE", wqe, 3736*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 3737*cdcd52d4SBartosz Sobczak irdma_get_cqp_reg_info(cqp, &val, &tail, &error); 3738*cdcd52d4SBartosz Sobczak 3739*cdcd52d4SBartosz Sobczak if (post_sq) { 3740*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 3741*cdcd52d4SBartosz Sobczak if (wait_type == IRDMA_CQP_WAIT_POLL_REGS) 3742*cdcd52d4SBartosz Sobczak ret_code = irdma_cqp_poll_registers(cqp, tail, 3743*cdcd52d4SBartosz Sobczak cqp->dev->hw_attrs.max_done_count); 3744*cdcd52d4SBartosz Sobczak else if (wait_type == IRDMA_CQP_WAIT_POLL_CQ) 3745*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_query_fpm_val_done(cqp); 3746*cdcd52d4SBartosz Sobczak } 3747*cdcd52d4SBartosz Sobczak 3748*cdcd52d4SBartosz Sobczak return ret_code; 3749*cdcd52d4SBartosz Sobczak } 3750*cdcd52d4SBartosz Sobczak 3751*cdcd52d4SBartosz Sobczak /** 3752*cdcd52d4SBartosz Sobczak * irdma_sc_ceq_init - initialize ceq 3753*cdcd52d4SBartosz Sobczak * @ceq: ceq sc structure 3754*cdcd52d4SBartosz Sobczak * @info: ceq initialization info 3755*cdcd52d4SBartosz Sobczak */ 3756*cdcd52d4SBartosz Sobczak int 3757*cdcd52d4SBartosz Sobczak irdma_sc_ceq_init(struct irdma_sc_ceq *ceq, 3758*cdcd52d4SBartosz Sobczak struct irdma_ceq_init_info *info) 3759*cdcd52d4SBartosz Sobczak { 3760*cdcd52d4SBartosz Sobczak u32 pble_obj_cnt; 3761*cdcd52d4SBartosz Sobczak 3762*cdcd52d4SBartosz Sobczak if (info->elem_cnt < info->dev->hw_attrs.min_hw_ceq_size || 3763*cdcd52d4SBartosz Sobczak info->elem_cnt > info->dev->hw_attrs.max_hw_ceq_size) 3764*cdcd52d4SBartosz Sobczak return -EINVAL; 3765*cdcd52d4SBartosz Sobczak 3766*cdcd52d4SBartosz Sobczak if (info->ceq_id > (info->dev->hmc_fpm_misc.max_ceqs - 1)) 3767*cdcd52d4SBartosz Sobczak return -EINVAL; 3768*cdcd52d4SBartosz Sobczak pble_obj_cnt = info->dev->hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].cnt; 3769*cdcd52d4SBartosz Sobczak 3770*cdcd52d4SBartosz Sobczak if (info->virtual_map && info->first_pm_pbl_idx >= pble_obj_cnt) 3771*cdcd52d4SBartosz Sobczak return -EINVAL; 3772*cdcd52d4SBartosz Sobczak 3773*cdcd52d4SBartosz Sobczak ceq->size = sizeof(*ceq); 3774*cdcd52d4SBartosz Sobczak ceq->ceqe_base = (struct irdma_ceqe *)info->ceqe_base; 3775*cdcd52d4SBartosz Sobczak ceq->ceq_id = info->ceq_id; 3776*cdcd52d4SBartosz Sobczak ceq->dev = info->dev; 3777*cdcd52d4SBartosz Sobczak ceq->elem_cnt = info->elem_cnt; 3778*cdcd52d4SBartosz Sobczak ceq->ceq_elem_pa = info->ceqe_pa; 3779*cdcd52d4SBartosz Sobczak ceq->virtual_map = info->virtual_map; 3780*cdcd52d4SBartosz Sobczak ceq->itr_no_expire = info->itr_no_expire; 3781*cdcd52d4SBartosz Sobczak ceq->reg_cq = info->reg_cq; 3782*cdcd52d4SBartosz Sobczak ceq->reg_cq_size = 0; 3783*cdcd52d4SBartosz Sobczak spin_lock_init(&ceq->req_cq_lock); 3784*cdcd52d4SBartosz Sobczak ceq->pbl_chunk_size = (ceq->virtual_map ? info->pbl_chunk_size : 0); 3785*cdcd52d4SBartosz Sobczak ceq->first_pm_pbl_idx = (ceq->virtual_map ? info->first_pm_pbl_idx : 0); 3786*cdcd52d4SBartosz Sobczak ceq->pbl_list = (ceq->virtual_map ? info->pbl_list : NULL); 3787*cdcd52d4SBartosz Sobczak ceq->tph_en = info->tph_en; 3788*cdcd52d4SBartosz Sobczak ceq->tph_val = info->tph_val; 3789*cdcd52d4SBartosz Sobczak ceq->vsi = info->vsi; 3790*cdcd52d4SBartosz Sobczak ceq->polarity = 1; 3791*cdcd52d4SBartosz Sobczak IRDMA_RING_INIT(ceq->ceq_ring, ceq->elem_cnt); 3792*cdcd52d4SBartosz Sobczak ceq->dev->ceq[info->ceq_id] = ceq; 3793*cdcd52d4SBartosz Sobczak 3794*cdcd52d4SBartosz Sobczak return 0; 3795*cdcd52d4SBartosz Sobczak } 3796*cdcd52d4SBartosz Sobczak 3797*cdcd52d4SBartosz Sobczak /** 3798*cdcd52d4SBartosz Sobczak * irdma_sc_ceq_create - create ceq wqe 3799*cdcd52d4SBartosz Sobczak * @ceq: ceq sc structure 3800*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 3801*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 3802*cdcd52d4SBartosz Sobczak */ 3803*cdcd52d4SBartosz Sobczak 3804*cdcd52d4SBartosz Sobczak static int 3805*cdcd52d4SBartosz Sobczak irdma_sc_ceq_create(struct irdma_sc_ceq *ceq, u64 scratch, 3806*cdcd52d4SBartosz Sobczak bool post_sq) 3807*cdcd52d4SBartosz Sobczak { 3808*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 3809*cdcd52d4SBartosz Sobczak __le64 *wqe; 3810*cdcd52d4SBartosz Sobczak u64 hdr; 3811*cdcd52d4SBartosz Sobczak 3812*cdcd52d4SBartosz Sobczak cqp = ceq->dev->cqp; 3813*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 3814*cdcd52d4SBartosz Sobczak if (!wqe) 3815*cdcd52d4SBartosz Sobczak return -ENOSPC; 3816*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, ceq->elem_cnt); 3817*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, 3818*cdcd52d4SBartosz Sobczak (ceq->virtual_map ? 0 : ceq->ceq_elem_pa)); 3819*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_48, 3820*cdcd52d4SBartosz Sobczak (ceq->virtual_map ? ceq->first_pm_pbl_idx : 0)); 3821*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_56, 3822*cdcd52d4SBartosz Sobczak LS_64(ceq->tph_val, IRDMA_CQPSQ_TPHVAL) | 3823*cdcd52d4SBartosz Sobczak LS_64(ceq->vsi->vsi_idx, IRDMA_CQPSQ_VSIIDX)); 3824*cdcd52d4SBartosz Sobczak hdr = LS_64(ceq->ceq_id, IRDMA_CQPSQ_CEQ_CEQID) | 3825*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_CREATE_CEQ, IRDMA_CQPSQ_OPCODE) | 3826*cdcd52d4SBartosz Sobczak LS_64(ceq->pbl_chunk_size, IRDMA_CQPSQ_CEQ_LPBLSIZE) | 3827*cdcd52d4SBartosz Sobczak LS_64(ceq->virtual_map, IRDMA_CQPSQ_CEQ_VMAP) | 3828*cdcd52d4SBartosz Sobczak LS_64(ceq->itr_no_expire, IRDMA_CQPSQ_CEQ_ITRNOEXPIRE) | 3829*cdcd52d4SBartosz Sobczak LS_64(ceq->tph_en, IRDMA_CQPSQ_TPHEN) | 3830*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 3831*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 3832*cdcd52d4SBartosz Sobczak 3833*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 3834*cdcd52d4SBartosz Sobczak 3835*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "CEQ_CREATE WQE", wqe, 3836*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 3837*cdcd52d4SBartosz Sobczak if (post_sq) 3838*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 3839*cdcd52d4SBartosz Sobczak 3840*cdcd52d4SBartosz Sobczak return 0; 3841*cdcd52d4SBartosz Sobczak } 3842*cdcd52d4SBartosz Sobczak 3843*cdcd52d4SBartosz Sobczak /** 3844*cdcd52d4SBartosz Sobczak * irdma_sc_cceq_create_done - poll for control ceq wqe to complete 3845*cdcd52d4SBartosz Sobczak * @ceq: ceq sc structure 3846*cdcd52d4SBartosz Sobczak */ 3847*cdcd52d4SBartosz Sobczak static int 3848*cdcd52d4SBartosz Sobczak irdma_sc_cceq_create_done(struct irdma_sc_ceq *ceq) 3849*cdcd52d4SBartosz Sobczak { 3850*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 3851*cdcd52d4SBartosz Sobczak 3852*cdcd52d4SBartosz Sobczak cqp = ceq->dev->cqp; 3853*cdcd52d4SBartosz Sobczak return irdma_sc_poll_for_cqp_op_done(cqp, IRDMA_CQP_OP_CREATE_CEQ, 3854*cdcd52d4SBartosz Sobczak NULL); 3855*cdcd52d4SBartosz Sobczak } 3856*cdcd52d4SBartosz Sobczak 3857*cdcd52d4SBartosz Sobczak /** 3858*cdcd52d4SBartosz Sobczak * irdma_sc_cceq_destroy_done - poll for destroy cceq to complete 3859*cdcd52d4SBartosz Sobczak * @ceq: ceq sc structure 3860*cdcd52d4SBartosz Sobczak */ 3861*cdcd52d4SBartosz Sobczak int 3862*cdcd52d4SBartosz Sobczak irdma_sc_cceq_destroy_done(struct irdma_sc_ceq *ceq) 3863*cdcd52d4SBartosz Sobczak { 3864*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 3865*cdcd52d4SBartosz Sobczak 3866*cdcd52d4SBartosz Sobczak if (ceq->reg_cq) 3867*cdcd52d4SBartosz Sobczak irdma_sc_remove_cq_ctx(ceq, ceq->dev->ccq); 3868*cdcd52d4SBartosz Sobczak 3869*cdcd52d4SBartosz Sobczak cqp = ceq->dev->cqp; 3870*cdcd52d4SBartosz Sobczak cqp->process_cqp_sds = irdma_update_sds_noccq; 3871*cdcd52d4SBartosz Sobczak 3872*cdcd52d4SBartosz Sobczak return irdma_sc_poll_for_cqp_op_done(cqp, IRDMA_CQP_OP_DESTROY_CEQ, 3873*cdcd52d4SBartosz Sobczak NULL); 3874*cdcd52d4SBartosz Sobczak } 3875*cdcd52d4SBartosz Sobczak 3876*cdcd52d4SBartosz Sobczak /** 3877*cdcd52d4SBartosz Sobczak * irdma_sc_cceq_create - create cceq 3878*cdcd52d4SBartosz Sobczak * @ceq: ceq sc structure 3879*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 3880*cdcd52d4SBartosz Sobczak */ 3881*cdcd52d4SBartosz Sobczak int 3882*cdcd52d4SBartosz Sobczak irdma_sc_cceq_create(struct irdma_sc_ceq *ceq, u64 scratch) 3883*cdcd52d4SBartosz Sobczak { 3884*cdcd52d4SBartosz Sobczak int ret_code; 3885*cdcd52d4SBartosz Sobczak struct irdma_sc_dev *dev = ceq->dev; 3886*cdcd52d4SBartosz Sobczak 3887*cdcd52d4SBartosz Sobczak dev->ccq->vsi = ceq->vsi; 3888*cdcd52d4SBartosz Sobczak if (ceq->reg_cq) { 3889*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_add_cq_ctx(ceq, ceq->dev->ccq); 3890*cdcd52d4SBartosz Sobczak if (ret_code) 3891*cdcd52d4SBartosz Sobczak return ret_code; 3892*cdcd52d4SBartosz Sobczak } 3893*cdcd52d4SBartosz Sobczak 3894*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_ceq_create(ceq, scratch, true); 3895*cdcd52d4SBartosz Sobczak if (!ret_code) 3896*cdcd52d4SBartosz Sobczak return irdma_sc_cceq_create_done(ceq); 3897*cdcd52d4SBartosz Sobczak 3898*cdcd52d4SBartosz Sobczak return ret_code; 3899*cdcd52d4SBartosz Sobczak } 3900*cdcd52d4SBartosz Sobczak 3901*cdcd52d4SBartosz Sobczak /** 3902*cdcd52d4SBartosz Sobczak * irdma_sc_ceq_destroy - destroy ceq 3903*cdcd52d4SBartosz Sobczak * @ceq: ceq sc structure 3904*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 3905*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 3906*cdcd52d4SBartosz Sobczak */ 3907*cdcd52d4SBartosz Sobczak int 3908*cdcd52d4SBartosz Sobczak irdma_sc_ceq_destroy(struct irdma_sc_ceq *ceq, u64 scratch, bool post_sq) 3909*cdcd52d4SBartosz Sobczak { 3910*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 3911*cdcd52d4SBartosz Sobczak __le64 *wqe; 3912*cdcd52d4SBartosz Sobczak u64 hdr; 3913*cdcd52d4SBartosz Sobczak 3914*cdcd52d4SBartosz Sobczak cqp = ceq->dev->cqp; 3915*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 3916*cdcd52d4SBartosz Sobczak if (!wqe) 3917*cdcd52d4SBartosz Sobczak return -ENOSPC; 3918*cdcd52d4SBartosz Sobczak 3919*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, ceq->elem_cnt); 3920*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_48, ceq->first_pm_pbl_idx); 3921*cdcd52d4SBartosz Sobczak hdr = ceq->ceq_id | 3922*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_DESTROY_CEQ, IRDMA_CQPSQ_OPCODE) | 3923*cdcd52d4SBartosz Sobczak LS_64(ceq->pbl_chunk_size, IRDMA_CQPSQ_CEQ_LPBLSIZE) | 3924*cdcd52d4SBartosz Sobczak LS_64(ceq->virtual_map, IRDMA_CQPSQ_CEQ_VMAP) | 3925*cdcd52d4SBartosz Sobczak LS_64(ceq->tph_en, IRDMA_CQPSQ_TPHEN) | 3926*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 3927*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 3928*cdcd52d4SBartosz Sobczak 3929*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 3930*cdcd52d4SBartosz Sobczak 3931*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "CEQ_DESTROY WQE", wqe, 3932*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 3933*cdcd52d4SBartosz Sobczak ceq->dev->ceq[ceq->ceq_id] = NULL; 3934*cdcd52d4SBartosz Sobczak if (post_sq) 3935*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 3936*cdcd52d4SBartosz Sobczak 3937*cdcd52d4SBartosz Sobczak return 0; 3938*cdcd52d4SBartosz Sobczak } 3939*cdcd52d4SBartosz Sobczak 3940*cdcd52d4SBartosz Sobczak /** 3941*cdcd52d4SBartosz Sobczak * irdma_sc_process_ceq - process ceq 3942*cdcd52d4SBartosz Sobczak * @dev: sc device struct 3943*cdcd52d4SBartosz Sobczak * @ceq: ceq sc structure 3944*cdcd52d4SBartosz Sobczak * 3945*cdcd52d4SBartosz Sobczak * It is expected caller serializes this function with cleanup_ceqes() 3946*cdcd52d4SBartosz Sobczak * because these functions manipulate the same ceq 3947*cdcd52d4SBartosz Sobczak */ 3948*cdcd52d4SBartosz Sobczak void * 3949*cdcd52d4SBartosz Sobczak irdma_sc_process_ceq(struct irdma_sc_dev *dev, struct irdma_sc_ceq *ceq) 3950*cdcd52d4SBartosz Sobczak { 3951*cdcd52d4SBartosz Sobczak u64 temp; 3952*cdcd52d4SBartosz Sobczak __le64 *ceqe; 3953*cdcd52d4SBartosz Sobczak struct irdma_sc_cq *cq = NULL; 3954*cdcd52d4SBartosz Sobczak struct irdma_sc_cq *temp_cq; 3955*cdcd52d4SBartosz Sobczak u8 polarity; 3956*cdcd52d4SBartosz Sobczak u32 cq_idx; 3957*cdcd52d4SBartosz Sobczak unsigned long flags; 3958*cdcd52d4SBartosz Sobczak 3959*cdcd52d4SBartosz Sobczak do { 3960*cdcd52d4SBartosz Sobczak cq_idx = 0; 3961*cdcd52d4SBartosz Sobczak ceqe = IRDMA_GET_CURRENT_CEQ_ELEM(ceq); 3962*cdcd52d4SBartosz Sobczak get_64bit_val(ceqe, IRDMA_BYTE_0, &temp); 3963*cdcd52d4SBartosz Sobczak polarity = (u8)RS_64(temp, IRDMA_CEQE_VALID); 3964*cdcd52d4SBartosz Sobczak if (polarity != ceq->polarity) 3965*cdcd52d4SBartosz Sobczak return NULL; 3966*cdcd52d4SBartosz Sobczak 3967*cdcd52d4SBartosz Sobczak temp_cq = (struct irdma_sc_cq *)(irdma_uintptr) LS_64_1(temp, 1); 3968*cdcd52d4SBartosz Sobczak if (!temp_cq) { 3969*cdcd52d4SBartosz Sobczak cq_idx = IRDMA_INVALID_CQ_IDX; 3970*cdcd52d4SBartosz Sobczak IRDMA_RING_MOVE_TAIL(ceq->ceq_ring); 3971*cdcd52d4SBartosz Sobczak 3972*cdcd52d4SBartosz Sobczak if (!IRDMA_RING_CURRENT_TAIL(ceq->ceq_ring)) 3973*cdcd52d4SBartosz Sobczak ceq->polarity ^= 1; 3974*cdcd52d4SBartosz Sobczak continue; 3975*cdcd52d4SBartosz Sobczak } 3976*cdcd52d4SBartosz Sobczak 3977*cdcd52d4SBartosz Sobczak cq = temp_cq; 3978*cdcd52d4SBartosz Sobczak if (ceq->reg_cq) { 3979*cdcd52d4SBartosz Sobczak spin_lock_irqsave(&ceq->req_cq_lock, flags); 3980*cdcd52d4SBartosz Sobczak cq_idx = irdma_sc_find_reg_cq(ceq, cq); 3981*cdcd52d4SBartosz Sobczak spin_unlock_irqrestore(&ceq->req_cq_lock, flags); 3982*cdcd52d4SBartosz Sobczak } 3983*cdcd52d4SBartosz Sobczak 3984*cdcd52d4SBartosz Sobczak IRDMA_RING_MOVE_TAIL(ceq->ceq_ring); 3985*cdcd52d4SBartosz Sobczak if (!IRDMA_RING_CURRENT_TAIL(ceq->ceq_ring)) 3986*cdcd52d4SBartosz Sobczak ceq->polarity ^= 1; 3987*cdcd52d4SBartosz Sobczak } while (cq_idx == IRDMA_INVALID_CQ_IDX); 3988*cdcd52d4SBartosz Sobczak 3989*cdcd52d4SBartosz Sobczak if (cq) { 3990*cdcd52d4SBartosz Sobczak cq->cq_uk.armed = false; 3991*cdcd52d4SBartosz Sobczak irdma_sc_cq_ack(cq); 3992*cdcd52d4SBartosz Sobczak } 3993*cdcd52d4SBartosz Sobczak return cq; 3994*cdcd52d4SBartosz Sobczak } 3995*cdcd52d4SBartosz Sobczak 3996*cdcd52d4SBartosz Sobczak /** 3997*cdcd52d4SBartosz Sobczak * irdma_sc_cleanup_ceqes - clear the valid ceqes ctx matching the cq 3998*cdcd52d4SBartosz Sobczak * @cq: cq for which the ceqes need to be cleaned up 3999*cdcd52d4SBartosz Sobczak * @ceq: ceq ptr 4000*cdcd52d4SBartosz Sobczak * 4001*cdcd52d4SBartosz Sobczak * The function is called after the cq is destroyed to cleanup 4002*cdcd52d4SBartosz Sobczak * its pending ceqe entries. It is expected caller serializes this 4003*cdcd52d4SBartosz Sobczak * function with process_ceq() in interrupt context. 4004*cdcd52d4SBartosz Sobczak */ 4005*cdcd52d4SBartosz Sobczak void 4006*cdcd52d4SBartosz Sobczak irdma_sc_cleanup_ceqes(struct irdma_sc_cq *cq, struct irdma_sc_ceq *ceq) 4007*cdcd52d4SBartosz Sobczak { 4008*cdcd52d4SBartosz Sobczak struct irdma_sc_cq *next_cq; 4009*cdcd52d4SBartosz Sobczak u8 ceq_polarity = ceq->polarity; 4010*cdcd52d4SBartosz Sobczak __le64 *ceqe; 4011*cdcd52d4SBartosz Sobczak u8 polarity; 4012*cdcd52d4SBartosz Sobczak u64 temp; 4013*cdcd52d4SBartosz Sobczak int next; 4014*cdcd52d4SBartosz Sobczak u32 i; 4015*cdcd52d4SBartosz Sobczak 4016*cdcd52d4SBartosz Sobczak next = IRDMA_RING_GET_NEXT_TAIL(ceq->ceq_ring, 0); 4017*cdcd52d4SBartosz Sobczak 4018*cdcd52d4SBartosz Sobczak for (i = 1; i <= IRDMA_RING_SIZE(*ceq); i++) { 4019*cdcd52d4SBartosz Sobczak ceqe = IRDMA_GET_CEQ_ELEM_AT_POS(ceq, next); 4020*cdcd52d4SBartosz Sobczak 4021*cdcd52d4SBartosz Sobczak get_64bit_val(ceqe, IRDMA_BYTE_0, &temp); 4022*cdcd52d4SBartosz Sobczak polarity = (u8)RS_64(temp, IRDMA_CEQE_VALID); 4023*cdcd52d4SBartosz Sobczak if (polarity != ceq_polarity) 4024*cdcd52d4SBartosz Sobczak return; 4025*cdcd52d4SBartosz Sobczak 4026*cdcd52d4SBartosz Sobczak next_cq = (struct irdma_sc_cq *)(irdma_uintptr) LS_64_1(temp, 1); 4027*cdcd52d4SBartosz Sobczak if (cq == next_cq) 4028*cdcd52d4SBartosz Sobczak set_64bit_val(ceqe, IRDMA_BYTE_0, temp & IRDMA_CEQE_VALID_M); 4029*cdcd52d4SBartosz Sobczak 4030*cdcd52d4SBartosz Sobczak next = IRDMA_RING_GET_NEXT_TAIL(ceq->ceq_ring, i); 4031*cdcd52d4SBartosz Sobczak if (!next) 4032*cdcd52d4SBartosz Sobczak ceq_polarity ^= 1; 4033*cdcd52d4SBartosz Sobczak } 4034*cdcd52d4SBartosz Sobczak } 4035*cdcd52d4SBartosz Sobczak 4036*cdcd52d4SBartosz Sobczak /** 4037*cdcd52d4SBartosz Sobczak * irdma_sc_aeq_init - initialize aeq 4038*cdcd52d4SBartosz Sobczak * @aeq: aeq structure ptr 4039*cdcd52d4SBartosz Sobczak * @info: aeq initialization info 4040*cdcd52d4SBartosz Sobczak */ 4041*cdcd52d4SBartosz Sobczak int 4042*cdcd52d4SBartosz Sobczak irdma_sc_aeq_init(struct irdma_sc_aeq *aeq, 4043*cdcd52d4SBartosz Sobczak struct irdma_aeq_init_info *info) 4044*cdcd52d4SBartosz Sobczak { 4045*cdcd52d4SBartosz Sobczak u32 pble_obj_cnt; 4046*cdcd52d4SBartosz Sobczak 4047*cdcd52d4SBartosz Sobczak if (info->elem_cnt < info->dev->hw_attrs.min_hw_aeq_size || 4048*cdcd52d4SBartosz Sobczak info->elem_cnt > info->dev->hw_attrs.max_hw_aeq_size) 4049*cdcd52d4SBartosz Sobczak return -EINVAL; 4050*cdcd52d4SBartosz Sobczak 4051*cdcd52d4SBartosz Sobczak pble_obj_cnt = info->dev->hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].cnt; 4052*cdcd52d4SBartosz Sobczak 4053*cdcd52d4SBartosz Sobczak if (info->virtual_map && info->first_pm_pbl_idx >= pble_obj_cnt) 4054*cdcd52d4SBartosz Sobczak return -EINVAL; 4055*cdcd52d4SBartosz Sobczak 4056*cdcd52d4SBartosz Sobczak aeq->size = sizeof(*aeq); 4057*cdcd52d4SBartosz Sobczak aeq->polarity = 1; 4058*cdcd52d4SBartosz Sobczak aeq->aeqe_base = (struct irdma_sc_aeqe *)info->aeqe_base; 4059*cdcd52d4SBartosz Sobczak aeq->dev = info->dev; 4060*cdcd52d4SBartosz Sobczak aeq->elem_cnt = info->elem_cnt; 4061*cdcd52d4SBartosz Sobczak aeq->aeq_elem_pa = info->aeq_elem_pa; 4062*cdcd52d4SBartosz Sobczak IRDMA_RING_INIT(aeq->aeq_ring, aeq->elem_cnt); 4063*cdcd52d4SBartosz Sobczak aeq->virtual_map = info->virtual_map; 4064*cdcd52d4SBartosz Sobczak aeq->pbl_list = (aeq->virtual_map ? info->pbl_list : NULL); 4065*cdcd52d4SBartosz Sobczak aeq->pbl_chunk_size = (aeq->virtual_map ? info->pbl_chunk_size : 0); 4066*cdcd52d4SBartosz Sobczak aeq->first_pm_pbl_idx = (aeq->virtual_map ? info->first_pm_pbl_idx : 0); 4067*cdcd52d4SBartosz Sobczak aeq->msix_idx = info->msix_idx; 4068*cdcd52d4SBartosz Sobczak info->dev->aeq = aeq; 4069*cdcd52d4SBartosz Sobczak 4070*cdcd52d4SBartosz Sobczak return 0; 4071*cdcd52d4SBartosz Sobczak } 4072*cdcd52d4SBartosz Sobczak 4073*cdcd52d4SBartosz Sobczak /** 4074*cdcd52d4SBartosz Sobczak * irdma_sc_aeq_create - create aeq 4075*cdcd52d4SBartosz Sobczak * @aeq: aeq structure ptr 4076*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 4077*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 4078*cdcd52d4SBartosz Sobczak */ 4079*cdcd52d4SBartosz Sobczak static int 4080*cdcd52d4SBartosz Sobczak irdma_sc_aeq_create(struct irdma_sc_aeq *aeq, u64 scratch, 4081*cdcd52d4SBartosz Sobczak bool post_sq) 4082*cdcd52d4SBartosz Sobczak { 4083*cdcd52d4SBartosz Sobczak __le64 *wqe; 4084*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 4085*cdcd52d4SBartosz Sobczak u64 hdr; 4086*cdcd52d4SBartosz Sobczak 4087*cdcd52d4SBartosz Sobczak cqp = aeq->dev->cqp; 4088*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 4089*cdcd52d4SBartosz Sobczak if (!wqe) 4090*cdcd52d4SBartosz Sobczak return -ENOSPC; 4091*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, aeq->elem_cnt); 4092*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, 4093*cdcd52d4SBartosz Sobczak (aeq->virtual_map ? 0 : aeq->aeq_elem_pa)); 4094*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_48, 4095*cdcd52d4SBartosz Sobczak (aeq->virtual_map ? aeq->first_pm_pbl_idx : 0)); 4096*cdcd52d4SBartosz Sobczak 4097*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMA_CQP_OP_CREATE_AEQ, IRDMA_CQPSQ_OPCODE) | 4098*cdcd52d4SBartosz Sobczak LS_64(aeq->pbl_chunk_size, IRDMA_CQPSQ_AEQ_LPBLSIZE) | 4099*cdcd52d4SBartosz Sobczak LS_64(aeq->virtual_map, IRDMA_CQPSQ_AEQ_VMAP) | 4100*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 4101*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 4102*cdcd52d4SBartosz Sobczak 4103*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 4104*cdcd52d4SBartosz Sobczak 4105*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "AEQ_CREATE WQE", wqe, 4106*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 4107*cdcd52d4SBartosz Sobczak if (post_sq) 4108*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 4109*cdcd52d4SBartosz Sobczak 4110*cdcd52d4SBartosz Sobczak return 0; 4111*cdcd52d4SBartosz Sobczak } 4112*cdcd52d4SBartosz Sobczak 4113*cdcd52d4SBartosz Sobczak /** 4114*cdcd52d4SBartosz Sobczak * irdma_sc_aeq_destroy - destroy aeq during close 4115*cdcd52d4SBartosz Sobczak * @aeq: aeq structure ptr 4116*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 4117*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 4118*cdcd52d4SBartosz Sobczak */ 4119*cdcd52d4SBartosz Sobczak static int 4120*cdcd52d4SBartosz Sobczak irdma_sc_aeq_destroy(struct irdma_sc_aeq *aeq, u64 scratch, 4121*cdcd52d4SBartosz Sobczak bool post_sq) 4122*cdcd52d4SBartosz Sobczak { 4123*cdcd52d4SBartosz Sobczak __le64 *wqe; 4124*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 4125*cdcd52d4SBartosz Sobczak struct irdma_sc_dev *dev; 4126*cdcd52d4SBartosz Sobczak u64 hdr; 4127*cdcd52d4SBartosz Sobczak 4128*cdcd52d4SBartosz Sobczak dev = aeq->dev; 4129*cdcd52d4SBartosz Sobczak writel(0, dev->hw_regs[IRDMA_PFINT_AEQCTL]); 4130*cdcd52d4SBartosz Sobczak 4131*cdcd52d4SBartosz Sobczak cqp = dev->cqp; 4132*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 4133*cdcd52d4SBartosz Sobczak if (!wqe) 4134*cdcd52d4SBartosz Sobczak return -ENOSPC; 4135*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, aeq->elem_cnt); 4136*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_48, aeq->first_pm_pbl_idx); 4137*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMA_CQP_OP_DESTROY_AEQ, IRDMA_CQPSQ_OPCODE) | 4138*cdcd52d4SBartosz Sobczak LS_64(aeq->pbl_chunk_size, IRDMA_CQPSQ_AEQ_LPBLSIZE) | 4139*cdcd52d4SBartosz Sobczak LS_64(aeq->virtual_map, IRDMA_CQPSQ_AEQ_VMAP) | 4140*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 4141*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 4142*cdcd52d4SBartosz Sobczak 4143*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 4144*cdcd52d4SBartosz Sobczak 4145*cdcd52d4SBartosz Sobczak irdma_debug_buf(dev, IRDMA_DEBUG_WQE, "AEQ_DESTROY WQE", wqe, 4146*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 4147*cdcd52d4SBartosz Sobczak if (post_sq) 4148*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 4149*cdcd52d4SBartosz Sobczak return 0; 4150*cdcd52d4SBartosz Sobczak } 4151*cdcd52d4SBartosz Sobczak 4152*cdcd52d4SBartosz Sobczak /** 4153*cdcd52d4SBartosz Sobczak * irdma_sc_get_next_aeqe - get next aeq entry 4154*cdcd52d4SBartosz Sobczak * @aeq: aeq structure ptr 4155*cdcd52d4SBartosz Sobczak * @info: aeqe info to be returned 4156*cdcd52d4SBartosz Sobczak */ 4157*cdcd52d4SBartosz Sobczak int 4158*cdcd52d4SBartosz Sobczak irdma_sc_get_next_aeqe(struct irdma_sc_aeq *aeq, 4159*cdcd52d4SBartosz Sobczak struct irdma_aeqe_info *info) 4160*cdcd52d4SBartosz Sobczak { 4161*cdcd52d4SBartosz Sobczak u64 temp, compl_ctx; 4162*cdcd52d4SBartosz Sobczak __le64 *aeqe; 4163*cdcd52d4SBartosz Sobczak u16 wqe_idx; 4164*cdcd52d4SBartosz Sobczak u8 ae_src; 4165*cdcd52d4SBartosz Sobczak u8 polarity; 4166*cdcd52d4SBartosz Sobczak 4167*cdcd52d4SBartosz Sobczak aeqe = IRDMA_GET_CURRENT_AEQ_ELEM(aeq); 4168*cdcd52d4SBartosz Sobczak get_64bit_val(aeqe, IRDMA_BYTE_0, &compl_ctx); 4169*cdcd52d4SBartosz Sobczak get_64bit_val(aeqe, IRDMA_BYTE_8, &temp); 4170*cdcd52d4SBartosz Sobczak polarity = (u8)RS_64(temp, IRDMA_AEQE_VALID); 4171*cdcd52d4SBartosz Sobczak 4172*cdcd52d4SBartosz Sobczak if (aeq->polarity != polarity) 4173*cdcd52d4SBartosz Sobczak return -ENOENT; 4174*cdcd52d4SBartosz Sobczak 4175*cdcd52d4SBartosz Sobczak irdma_debug_buf(aeq->dev, IRDMA_DEBUG_WQE, "AEQ_ENTRY WQE", aeqe, 16); 4176*cdcd52d4SBartosz Sobczak 4177*cdcd52d4SBartosz Sobczak ae_src = (u8)RS_64(temp, IRDMA_AEQE_AESRC); 4178*cdcd52d4SBartosz Sobczak wqe_idx = (u16)RS_64(temp, IRDMA_AEQE_WQDESCIDX); 4179*cdcd52d4SBartosz Sobczak info->qp_cq_id = (u32)RS_64(temp, IRDMA_AEQE_QPCQID_LOW) | 4180*cdcd52d4SBartosz Sobczak ((u32)RS_64(temp, IRDMA_AEQE_QPCQID_HI) << 18); 4181*cdcd52d4SBartosz Sobczak info->ae_id = (u16)RS_64(temp, IRDMA_AEQE_AECODE); 4182*cdcd52d4SBartosz Sobczak info->tcp_state = (u8)RS_64(temp, IRDMA_AEQE_TCPSTATE); 4183*cdcd52d4SBartosz Sobczak info->iwarp_state = (u8)RS_64(temp, IRDMA_AEQE_IWSTATE); 4184*cdcd52d4SBartosz Sobczak info->q2_data_written = (u8)RS_64(temp, IRDMA_AEQE_Q2DATA); 4185*cdcd52d4SBartosz Sobczak info->aeqe_overflow = (bool)RS_64(temp, IRDMA_AEQE_OVERFLOW); 4186*cdcd52d4SBartosz Sobczak 4187*cdcd52d4SBartosz Sobczak info->ae_src = ae_src; 4188*cdcd52d4SBartosz Sobczak switch (info->ae_id) { 4189*cdcd52d4SBartosz Sobczak case IRDMA_AE_PRIV_OPERATION_DENIED: 4190*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_INVALIDATE_TYPE1_MW: 4191*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_MWBIND_ZERO_BASED_TYPE1_MW: 4192*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_FASTREG_INVALID_PBL_HPS_CFG: 4193*cdcd52d4SBartosz Sobczak case IRDMA_AE_AMP_FASTREG_PBLE_MISMATCH: 4194*cdcd52d4SBartosz Sobczak case IRDMA_AE_UDA_XMIT_DGRAM_TOO_LONG: 4195*cdcd52d4SBartosz Sobczak case IRDMA_AE_UDA_XMIT_BAD_PD: 4196*cdcd52d4SBartosz Sobczak case IRDMA_AE_UDA_XMIT_DGRAM_TOO_SHORT: 4197*cdcd52d4SBartosz Sobczak case IRDMA_AE_BAD_CLOSE: 4198*cdcd52d4SBartosz Sobczak case IRDMA_AE_RDMA_READ_WHILE_ORD_ZERO: 4199*cdcd52d4SBartosz Sobczak case IRDMA_AE_STAG_ZERO_INVALID: 4200*cdcd52d4SBartosz Sobczak case IRDMA_AE_IB_RREQ_AND_Q1_FULL: 4201*cdcd52d4SBartosz Sobczak case IRDMA_AE_IB_INVALID_REQUEST: 4202*cdcd52d4SBartosz Sobczak case IRDMA_AE_WQE_UNEXPECTED_OPCODE: 4203*cdcd52d4SBartosz Sobczak case IRDMA_AE_IB_REMOTE_ACCESS_ERROR: 4204*cdcd52d4SBartosz Sobczak case IRDMA_AE_IB_REMOTE_OP_ERROR: 4205*cdcd52d4SBartosz Sobczak case IRDMA_AE_DDP_UBE_INVALID_DDP_VERSION: 4206*cdcd52d4SBartosz Sobczak case IRDMA_AE_DDP_UBE_INVALID_MO: 4207*cdcd52d4SBartosz Sobczak case IRDMA_AE_DDP_UBE_INVALID_QN: 4208*cdcd52d4SBartosz Sobczak case IRDMA_AE_DDP_NO_L_BIT: 4209*cdcd52d4SBartosz Sobczak case IRDMA_AE_RDMAP_ROE_INVALID_RDMAP_VERSION: 4210*cdcd52d4SBartosz Sobczak case IRDMA_AE_RDMAP_ROE_UNEXPECTED_OPCODE: 4211*cdcd52d4SBartosz Sobczak case IRDMA_AE_ROE_INVALID_RDMA_READ_REQUEST: 4212*cdcd52d4SBartosz Sobczak case IRDMA_AE_ROE_INVALID_RDMA_WRITE_OR_READ_RESP: 4213*cdcd52d4SBartosz Sobczak case IRDMA_AE_ROCE_RSP_LENGTH_ERROR: 4214*cdcd52d4SBartosz Sobczak case IRDMA_AE_INVALID_ARP_ENTRY: 4215*cdcd52d4SBartosz Sobczak case IRDMA_AE_INVALID_TCP_OPTION_RCVD: 4216*cdcd52d4SBartosz Sobczak case IRDMA_AE_STALE_ARP_ENTRY: 4217*cdcd52d4SBartosz Sobczak case IRDMA_AE_INVALID_AH_ENTRY: 4218*cdcd52d4SBartosz Sobczak case IRDMA_AE_LLP_RECEIVED_MPA_CRC_ERROR: 4219*cdcd52d4SBartosz Sobczak case IRDMA_AE_LLP_SEGMENT_TOO_SMALL: 4220*cdcd52d4SBartosz Sobczak case IRDMA_AE_LLP_TOO_MANY_RETRIES: 4221*cdcd52d4SBartosz Sobczak case IRDMA_AE_LLP_DOUBT_REACHABILITY: 4222*cdcd52d4SBartosz Sobczak case IRDMA_AE_LLP_CONNECTION_ESTABLISHED: 4223*cdcd52d4SBartosz Sobczak case IRDMA_AE_RESET_SENT: 4224*cdcd52d4SBartosz Sobczak case IRDMA_AE_TERMINATE_SENT: 4225*cdcd52d4SBartosz Sobczak case IRDMA_AE_RESET_NOT_SENT: 4226*cdcd52d4SBartosz Sobczak case IRDMA_AE_LCE_QP_CATASTROPHIC: 4227*cdcd52d4SBartosz Sobczak case IRDMA_AE_QP_SUSPEND_COMPLETE: 4228*cdcd52d4SBartosz Sobczak case IRDMA_AE_UDA_L4LEN_INVALID: 4229*cdcd52d4SBartosz Sobczak info->qp = true; 4230*cdcd52d4SBartosz Sobczak info->compl_ctx = compl_ctx; 4231*cdcd52d4SBartosz Sobczak break; 4232*cdcd52d4SBartosz Sobczak case IRDMA_AE_LCE_CQ_CATASTROPHIC: 4233*cdcd52d4SBartosz Sobczak info->cq = true; 4234*cdcd52d4SBartosz Sobczak info->compl_ctx = LS_64_1(compl_ctx, 1); 4235*cdcd52d4SBartosz Sobczak ae_src = IRDMA_AE_SOURCE_RSVD; 4236*cdcd52d4SBartosz Sobczak break; 4237*cdcd52d4SBartosz Sobczak case IRDMA_AE_ROCE_EMPTY_MCG: 4238*cdcd52d4SBartosz Sobczak case IRDMA_AE_ROCE_BAD_MC_IP_ADDR: 4239*cdcd52d4SBartosz Sobczak case IRDMA_AE_ROCE_BAD_MC_QPID: 4240*cdcd52d4SBartosz Sobczak case IRDMA_AE_MCG_QP_PROTOCOL_MISMATCH: 4241*cdcd52d4SBartosz Sobczak /* fallthrough */ 4242*cdcd52d4SBartosz Sobczak case IRDMA_AE_LLP_CONNECTION_RESET: 4243*cdcd52d4SBartosz Sobczak case IRDMA_AE_LLP_SYN_RECEIVED: 4244*cdcd52d4SBartosz Sobczak case IRDMA_AE_LLP_FIN_RECEIVED: 4245*cdcd52d4SBartosz Sobczak case IRDMA_AE_LLP_CLOSE_COMPLETE: 4246*cdcd52d4SBartosz Sobczak case IRDMA_AE_LLP_TERMINATE_RECEIVED: 4247*cdcd52d4SBartosz Sobczak case IRDMA_AE_RDMAP_ROE_BAD_LLP_CLOSE: 4248*cdcd52d4SBartosz Sobczak ae_src = IRDMA_AE_SOURCE_RSVD; 4249*cdcd52d4SBartosz Sobczak info->qp = true; 4250*cdcd52d4SBartosz Sobczak info->compl_ctx = compl_ctx; 4251*cdcd52d4SBartosz Sobczak break; 4252*cdcd52d4SBartosz Sobczak default: 4253*cdcd52d4SBartosz Sobczak break; 4254*cdcd52d4SBartosz Sobczak } 4255*cdcd52d4SBartosz Sobczak 4256*cdcd52d4SBartosz Sobczak switch (ae_src) { 4257*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_RQ: 4258*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_RQ_0011: 4259*cdcd52d4SBartosz Sobczak info->qp = true; 4260*cdcd52d4SBartosz Sobczak info->rq = true; 4261*cdcd52d4SBartosz Sobczak info->wqe_idx = wqe_idx; 4262*cdcd52d4SBartosz Sobczak info->compl_ctx = compl_ctx; 4263*cdcd52d4SBartosz Sobczak break; 4264*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_CQ: 4265*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_CQ_0110: 4266*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_CQ_1010: 4267*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_CQ_1110: 4268*cdcd52d4SBartosz Sobczak info->cq = true; 4269*cdcd52d4SBartosz Sobczak info->compl_ctx = LS_64_1(compl_ctx, 1); 4270*cdcd52d4SBartosz Sobczak break; 4271*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_SQ: 4272*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_SQ_0111: 4273*cdcd52d4SBartosz Sobczak info->qp = true; 4274*cdcd52d4SBartosz Sobczak info->sq = true; 4275*cdcd52d4SBartosz Sobczak info->wqe_idx = wqe_idx; 4276*cdcd52d4SBartosz Sobczak info->compl_ctx = compl_ctx; 4277*cdcd52d4SBartosz Sobczak break; 4278*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_IN_WR: 4279*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_IN_RR: 4280*cdcd52d4SBartosz Sobczak info->qp = true; 4281*cdcd52d4SBartosz Sobczak info->compl_ctx = compl_ctx; 4282*cdcd52d4SBartosz Sobczak info->in_rdrsp_wr = true; 4283*cdcd52d4SBartosz Sobczak break; 4284*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_OUT_RR: 4285*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_OUT_RR_1111: 4286*cdcd52d4SBartosz Sobczak info->qp = true; 4287*cdcd52d4SBartosz Sobczak info->compl_ctx = compl_ctx; 4288*cdcd52d4SBartosz Sobczak info->out_rdrsp = true; 4289*cdcd52d4SBartosz Sobczak break; 4290*cdcd52d4SBartosz Sobczak case IRDMA_AE_SOURCE_RSVD: 4291*cdcd52d4SBartosz Sobczak default: 4292*cdcd52d4SBartosz Sobczak break; 4293*cdcd52d4SBartosz Sobczak } 4294*cdcd52d4SBartosz Sobczak 4295*cdcd52d4SBartosz Sobczak IRDMA_RING_MOVE_TAIL(aeq->aeq_ring); 4296*cdcd52d4SBartosz Sobczak if (!IRDMA_RING_CURRENT_TAIL(aeq->aeq_ring)) 4297*cdcd52d4SBartosz Sobczak aeq->polarity ^= 1; 4298*cdcd52d4SBartosz Sobczak 4299*cdcd52d4SBartosz Sobczak return 0; 4300*cdcd52d4SBartosz Sobczak } 4301*cdcd52d4SBartosz Sobczak 4302*cdcd52d4SBartosz Sobczak /** 4303*cdcd52d4SBartosz Sobczak * irdma_sc_repost_aeq_entries - repost completed aeq entries 4304*cdcd52d4SBartosz Sobczak * @dev: sc device struct 4305*cdcd52d4SBartosz Sobczak * @count: allocate count 4306*cdcd52d4SBartosz Sobczak */ 4307*cdcd52d4SBartosz Sobczak int 4308*cdcd52d4SBartosz Sobczak irdma_sc_repost_aeq_entries(struct irdma_sc_dev *dev, u32 count) 4309*cdcd52d4SBartosz Sobczak { 4310*cdcd52d4SBartosz Sobczak writel(count, dev->hw_regs[IRDMA_AEQALLOC]); 4311*cdcd52d4SBartosz Sobczak 4312*cdcd52d4SBartosz Sobczak return 0; 4313*cdcd52d4SBartosz Sobczak } 4314*cdcd52d4SBartosz Sobczak 4315*cdcd52d4SBartosz Sobczak /** 4316*cdcd52d4SBartosz Sobczak * irdma_sc_ccq_init - initialize control cq 4317*cdcd52d4SBartosz Sobczak * @cq: sc's cq ctruct 4318*cdcd52d4SBartosz Sobczak * @info: info for control cq initialization 4319*cdcd52d4SBartosz Sobczak */ 4320*cdcd52d4SBartosz Sobczak int 4321*cdcd52d4SBartosz Sobczak irdma_sc_ccq_init(struct irdma_sc_cq *cq, struct irdma_ccq_init_info *info) 4322*cdcd52d4SBartosz Sobczak { 4323*cdcd52d4SBartosz Sobczak u32 pble_obj_cnt; 4324*cdcd52d4SBartosz Sobczak 4325*cdcd52d4SBartosz Sobczak if (info->num_elem < info->dev->hw_attrs.uk_attrs.min_hw_cq_size || 4326*cdcd52d4SBartosz Sobczak info->num_elem > info->dev->hw_attrs.uk_attrs.max_hw_cq_size) 4327*cdcd52d4SBartosz Sobczak return -EINVAL; 4328*cdcd52d4SBartosz Sobczak 4329*cdcd52d4SBartosz Sobczak if (info->ceq_id > (info->dev->hmc_fpm_misc.max_ceqs - 1)) 4330*cdcd52d4SBartosz Sobczak return -EINVAL; 4331*cdcd52d4SBartosz Sobczak 4332*cdcd52d4SBartosz Sobczak pble_obj_cnt = info->dev->hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].cnt; 4333*cdcd52d4SBartosz Sobczak 4334*cdcd52d4SBartosz Sobczak if (info->virtual_map && info->first_pm_pbl_idx >= pble_obj_cnt) 4335*cdcd52d4SBartosz Sobczak return -EINVAL; 4336*cdcd52d4SBartosz Sobczak 4337*cdcd52d4SBartosz Sobczak cq->cq_pa = info->cq_pa; 4338*cdcd52d4SBartosz Sobczak cq->cq_uk.cq_base = info->cq_base; 4339*cdcd52d4SBartosz Sobczak cq->shadow_area_pa = info->shadow_area_pa; 4340*cdcd52d4SBartosz Sobczak cq->cq_uk.shadow_area = info->shadow_area; 4341*cdcd52d4SBartosz Sobczak cq->shadow_read_threshold = info->shadow_read_threshold; 4342*cdcd52d4SBartosz Sobczak cq->dev = info->dev; 4343*cdcd52d4SBartosz Sobczak cq->ceq_id = info->ceq_id; 4344*cdcd52d4SBartosz Sobczak cq->cq_uk.cq_size = info->num_elem; 4345*cdcd52d4SBartosz Sobczak cq->cq_type = IRDMA_CQ_TYPE_CQP; 4346*cdcd52d4SBartosz Sobczak cq->ceqe_mask = info->ceqe_mask; 4347*cdcd52d4SBartosz Sobczak IRDMA_RING_INIT(cq->cq_uk.cq_ring, info->num_elem); 4348*cdcd52d4SBartosz Sobczak cq->cq_uk.cq_id = 0; /* control cq is id 0 always */ 4349*cdcd52d4SBartosz Sobczak cq->ceq_id_valid = info->ceq_id_valid; 4350*cdcd52d4SBartosz Sobczak cq->tph_en = info->tph_en; 4351*cdcd52d4SBartosz Sobczak cq->tph_val = info->tph_val; 4352*cdcd52d4SBartosz Sobczak cq->cq_uk.avoid_mem_cflct = info->avoid_mem_cflct; 4353*cdcd52d4SBartosz Sobczak cq->pbl_list = info->pbl_list; 4354*cdcd52d4SBartosz Sobczak cq->virtual_map = info->virtual_map; 4355*cdcd52d4SBartosz Sobczak cq->pbl_chunk_size = info->pbl_chunk_size; 4356*cdcd52d4SBartosz Sobczak cq->first_pm_pbl_idx = info->first_pm_pbl_idx; 4357*cdcd52d4SBartosz Sobczak cq->cq_uk.polarity = true; 4358*cdcd52d4SBartosz Sobczak cq->vsi = info->vsi; 4359*cdcd52d4SBartosz Sobczak cq->cq_uk.cq_ack_db = cq->dev->cq_ack_db; 4360*cdcd52d4SBartosz Sobczak 4361*cdcd52d4SBartosz Sobczak /* Only applicable to CQs other than CCQ so initialize to zero */ 4362*cdcd52d4SBartosz Sobczak cq->cq_uk.cqe_alloc_db = NULL; 4363*cdcd52d4SBartosz Sobczak 4364*cdcd52d4SBartosz Sobczak info->dev->ccq = cq; 4365*cdcd52d4SBartosz Sobczak return 0; 4366*cdcd52d4SBartosz Sobczak } 4367*cdcd52d4SBartosz Sobczak 4368*cdcd52d4SBartosz Sobczak /** 4369*cdcd52d4SBartosz Sobczak * irdma_sc_ccq_create_done - poll cqp for ccq create 4370*cdcd52d4SBartosz Sobczak * @ccq: ccq sc struct 4371*cdcd52d4SBartosz Sobczak */ 4372*cdcd52d4SBartosz Sobczak static inline int 4373*cdcd52d4SBartosz Sobczak irdma_sc_ccq_create_done(struct irdma_sc_cq *ccq) 4374*cdcd52d4SBartosz Sobczak { 4375*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 4376*cdcd52d4SBartosz Sobczak 4377*cdcd52d4SBartosz Sobczak cqp = ccq->dev->cqp; 4378*cdcd52d4SBartosz Sobczak 4379*cdcd52d4SBartosz Sobczak return irdma_sc_poll_for_cqp_op_done(cqp, IRDMA_CQP_OP_CREATE_CQ, NULL); 4380*cdcd52d4SBartosz Sobczak } 4381*cdcd52d4SBartosz Sobczak 4382*cdcd52d4SBartosz Sobczak /** 4383*cdcd52d4SBartosz Sobczak * irdma_sc_ccq_create - create control cq 4384*cdcd52d4SBartosz Sobczak * @ccq: ccq sc struct 4385*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 4386*cdcd52d4SBartosz Sobczak * @check_overflow: overlow flag for ccq 4387*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 4388*cdcd52d4SBartosz Sobczak */ 4389*cdcd52d4SBartosz Sobczak int 4390*cdcd52d4SBartosz Sobczak irdma_sc_ccq_create(struct irdma_sc_cq *ccq, u64 scratch, 4391*cdcd52d4SBartosz Sobczak bool check_overflow, bool post_sq) 4392*cdcd52d4SBartosz Sobczak { 4393*cdcd52d4SBartosz Sobczak int ret_code; 4394*cdcd52d4SBartosz Sobczak 4395*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_cq_create(ccq, scratch, check_overflow, post_sq); 4396*cdcd52d4SBartosz Sobczak if (ret_code) 4397*cdcd52d4SBartosz Sobczak return ret_code; 4398*cdcd52d4SBartosz Sobczak 4399*cdcd52d4SBartosz Sobczak if (post_sq) { 4400*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_ccq_create_done(ccq); 4401*cdcd52d4SBartosz Sobczak if (ret_code) 4402*cdcd52d4SBartosz Sobczak return ret_code; 4403*cdcd52d4SBartosz Sobczak } 4404*cdcd52d4SBartosz Sobczak ccq->dev->cqp->process_cqp_sds = irdma_cqp_sds_cmd; 4405*cdcd52d4SBartosz Sobczak 4406*cdcd52d4SBartosz Sobczak return 0; 4407*cdcd52d4SBartosz Sobczak } 4408*cdcd52d4SBartosz Sobczak 4409*cdcd52d4SBartosz Sobczak /** 4410*cdcd52d4SBartosz Sobczak * irdma_sc_ccq_destroy - destroy ccq during close 4411*cdcd52d4SBartosz Sobczak * @ccq: ccq sc struct 4412*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 4413*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 4414*cdcd52d4SBartosz Sobczak */ 4415*cdcd52d4SBartosz Sobczak int 4416*cdcd52d4SBartosz Sobczak irdma_sc_ccq_destroy(struct irdma_sc_cq *ccq, u64 scratch, bool post_sq) 4417*cdcd52d4SBartosz Sobczak { 4418*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp; 4419*cdcd52d4SBartosz Sobczak __le64 *wqe; 4420*cdcd52d4SBartosz Sobczak u64 hdr; 4421*cdcd52d4SBartosz Sobczak int ret_code = 0; 4422*cdcd52d4SBartosz Sobczak u32 tail, val, error; 4423*cdcd52d4SBartosz Sobczak 4424*cdcd52d4SBartosz Sobczak cqp = ccq->dev->cqp; 4425*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 4426*cdcd52d4SBartosz Sobczak if (!wqe) 4427*cdcd52d4SBartosz Sobczak return -ENOSPC; 4428*cdcd52d4SBartosz Sobczak 4429*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_0, ccq->cq_uk.cq_size); 4430*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, RS_64_1(ccq, 1)); 4431*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, ccq->shadow_area_pa); 4432*cdcd52d4SBartosz Sobczak 4433*cdcd52d4SBartosz Sobczak hdr = ccq->cq_uk.cq_id | 4434*cdcd52d4SBartosz Sobczak FLD_LS_64(ccq->dev, (ccq->ceq_id_valid ? ccq->ceq_id : 0), 4435*cdcd52d4SBartosz Sobczak IRDMA_CQPSQ_CQ_CEQID) | 4436*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_DESTROY_CQ, IRDMA_CQPSQ_OPCODE) | 4437*cdcd52d4SBartosz Sobczak LS_64(ccq->ceqe_mask, IRDMA_CQPSQ_CQ_ENCEQEMASK) | 4438*cdcd52d4SBartosz Sobczak LS_64(ccq->ceq_id_valid, IRDMA_CQPSQ_CQ_CEQIDVALID) | 4439*cdcd52d4SBartosz Sobczak LS_64(ccq->tph_en, IRDMA_CQPSQ_TPHEN) | 4440*cdcd52d4SBartosz Sobczak LS_64(ccq->cq_uk.avoid_mem_cflct, IRDMA_CQPSQ_CQ_AVOIDMEMCNFLCT) | 4441*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 4442*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 4443*cdcd52d4SBartosz Sobczak 4444*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 4445*cdcd52d4SBartosz Sobczak 4446*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "CCQ_DESTROY WQE", wqe, 4447*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 4448*cdcd52d4SBartosz Sobczak irdma_get_cqp_reg_info(cqp, &val, &tail, &error); 4449*cdcd52d4SBartosz Sobczak 4450*cdcd52d4SBartosz Sobczak if (post_sq) { 4451*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 4452*cdcd52d4SBartosz Sobczak ret_code = irdma_cqp_poll_registers(cqp, tail, 4453*cdcd52d4SBartosz Sobczak cqp->dev->hw_attrs.max_done_count); 4454*cdcd52d4SBartosz Sobczak } 4455*cdcd52d4SBartosz Sobczak 4456*cdcd52d4SBartosz Sobczak cqp->process_cqp_sds = irdma_update_sds_noccq; 4457*cdcd52d4SBartosz Sobczak 4458*cdcd52d4SBartosz Sobczak return ret_code; 4459*cdcd52d4SBartosz Sobczak } 4460*cdcd52d4SBartosz Sobczak 4461*cdcd52d4SBartosz Sobczak /** 4462*cdcd52d4SBartosz Sobczak * irdma_sc_init_iw_hmc() - queries fpm values using cqp and populates hmc_info 4463*cdcd52d4SBartosz Sobczak * @dev : ptr to irdma_dev struct 4464*cdcd52d4SBartosz Sobczak * @hmc_fn_id: hmc function id 4465*cdcd52d4SBartosz Sobczak */ 4466*cdcd52d4SBartosz Sobczak int 4467*cdcd52d4SBartosz Sobczak irdma_sc_init_iw_hmc(struct irdma_sc_dev *dev, u8 hmc_fn_id) 4468*cdcd52d4SBartosz Sobczak { 4469*cdcd52d4SBartosz Sobczak struct irdma_hmc_info *hmc_info; 4470*cdcd52d4SBartosz Sobczak struct irdma_hmc_fpm_misc *hmc_fpm_misc; 4471*cdcd52d4SBartosz Sobczak struct irdma_dma_mem query_fpm_mem; 4472*cdcd52d4SBartosz Sobczak int ret_code = 0; 4473*cdcd52d4SBartosz Sobczak u8 wait_type; 4474*cdcd52d4SBartosz Sobczak 4475*cdcd52d4SBartosz Sobczak hmc_info = dev->hmc_info; 4476*cdcd52d4SBartosz Sobczak hmc_fpm_misc = &dev->hmc_fpm_misc; 4477*cdcd52d4SBartosz Sobczak query_fpm_mem.pa = dev->fpm_query_buf_pa; 4478*cdcd52d4SBartosz Sobczak query_fpm_mem.va = dev->fpm_query_buf; 4479*cdcd52d4SBartosz Sobczak hmc_info->hmc_fn_id = hmc_fn_id; 4480*cdcd52d4SBartosz Sobczak wait_type = (u8)IRDMA_CQP_WAIT_POLL_REGS; 4481*cdcd52d4SBartosz Sobczak 4482*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_query_fpm_val(dev->cqp, 0, hmc_info->hmc_fn_id, 4483*cdcd52d4SBartosz Sobczak &query_fpm_mem, true, wait_type); 4484*cdcd52d4SBartosz Sobczak if (ret_code) 4485*cdcd52d4SBartosz Sobczak return ret_code; 4486*cdcd52d4SBartosz Sobczak 4487*cdcd52d4SBartosz Sobczak /* parse the fpm_query_buf and fill hmc obj info */ 4488*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_parse_fpm_query_buf(dev, query_fpm_mem.va, hmc_info, 4489*cdcd52d4SBartosz Sobczak hmc_fpm_misc); 4490*cdcd52d4SBartosz Sobczak 4491*cdcd52d4SBartosz Sobczak irdma_debug_buf(dev, IRDMA_DEBUG_HMC, "QUERY FPM BUFFER", 4492*cdcd52d4SBartosz Sobczak query_fpm_mem.va, IRDMA_QUERY_FPM_BUF_SIZE); 4493*cdcd52d4SBartosz Sobczak return ret_code; 4494*cdcd52d4SBartosz Sobczak } 4495*cdcd52d4SBartosz Sobczak 4496*cdcd52d4SBartosz Sobczak /** 4497*cdcd52d4SBartosz Sobczak * irdma_sc_cfg_iw_fpm() - commits hmc obj cnt values using cqp 4498*cdcd52d4SBartosz Sobczak * command and populates fpm base address in hmc_info 4499*cdcd52d4SBartosz Sobczak * @dev : ptr to irdma_dev struct 4500*cdcd52d4SBartosz Sobczak * @hmc_fn_id: hmc function id 4501*cdcd52d4SBartosz Sobczak */ 4502*cdcd52d4SBartosz Sobczak static int 4503*cdcd52d4SBartosz Sobczak irdma_sc_cfg_iw_fpm(struct irdma_sc_dev *dev, u8 hmc_fn_id) 4504*cdcd52d4SBartosz Sobczak { 4505*cdcd52d4SBartosz Sobczak struct irdma_hmc_obj_info *obj_info; 4506*cdcd52d4SBartosz Sobczak __le64 *buf; 4507*cdcd52d4SBartosz Sobczak struct irdma_hmc_info *hmc_info; 4508*cdcd52d4SBartosz Sobczak struct irdma_dma_mem commit_fpm_mem; 4509*cdcd52d4SBartosz Sobczak int ret_code = 0; 4510*cdcd52d4SBartosz Sobczak u8 wait_type; 4511*cdcd52d4SBartosz Sobczak 4512*cdcd52d4SBartosz Sobczak hmc_info = dev->hmc_info; 4513*cdcd52d4SBartosz Sobczak obj_info = hmc_info->hmc_obj; 4514*cdcd52d4SBartosz Sobczak buf = dev->fpm_commit_buf; 4515*cdcd52d4SBartosz Sobczak 4516*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_0, (u64)obj_info[IRDMA_HMC_IW_QP].cnt); 4517*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_8, (u64)obj_info[IRDMA_HMC_IW_CQ].cnt); 4518*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_16, (u64)0); /* RSRVD */ 4519*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_24, (u64)obj_info[IRDMA_HMC_IW_HTE].cnt); 4520*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_32, (u64)obj_info[IRDMA_HMC_IW_ARP].cnt); 4521*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_40, (u64)0); /* RSVD */ 4522*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_48, (u64)obj_info[IRDMA_HMC_IW_MR].cnt); 4523*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_56, (u64)obj_info[IRDMA_HMC_IW_XF].cnt); 4524*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_64, (u64)obj_info[IRDMA_HMC_IW_XFFL].cnt); 4525*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_72, (u64)obj_info[IRDMA_HMC_IW_Q1].cnt); 4526*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_80, (u64)obj_info[IRDMA_HMC_IW_Q1FL].cnt); 4527*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_88, 4528*cdcd52d4SBartosz Sobczak (u64)obj_info[IRDMA_HMC_IW_TIMER].cnt); 4529*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_96, 4530*cdcd52d4SBartosz Sobczak (u64)obj_info[IRDMA_HMC_IW_FSIMC].cnt); 4531*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_104, 4532*cdcd52d4SBartosz Sobczak (u64)obj_info[IRDMA_HMC_IW_FSIAV].cnt); 4533*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_112, 4534*cdcd52d4SBartosz Sobczak (u64)obj_info[IRDMA_HMC_IW_PBLE].cnt); 4535*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_120, (u64)0); /* RSVD */ 4536*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_128, (u64)obj_info[IRDMA_HMC_IW_RRF].cnt); 4537*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_136, 4538*cdcd52d4SBartosz Sobczak (u64)obj_info[IRDMA_HMC_IW_RRFFL].cnt); 4539*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_144, (u64)obj_info[IRDMA_HMC_IW_HDR].cnt); 4540*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_152, (u64)obj_info[IRDMA_HMC_IW_MD].cnt); 4541*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_160, 4542*cdcd52d4SBartosz Sobczak (u64)obj_info[IRDMA_HMC_IW_OOISC].cnt); 4543*cdcd52d4SBartosz Sobczak set_64bit_val(buf, IRDMA_BYTE_168, 4544*cdcd52d4SBartosz Sobczak (u64)obj_info[IRDMA_HMC_IW_OOISCFFL].cnt); 4545*cdcd52d4SBartosz Sobczak commit_fpm_mem.pa = dev->fpm_commit_buf_pa; 4546*cdcd52d4SBartosz Sobczak commit_fpm_mem.va = dev->fpm_commit_buf; 4547*cdcd52d4SBartosz Sobczak 4548*cdcd52d4SBartosz Sobczak wait_type = (u8)IRDMA_CQP_WAIT_POLL_REGS; 4549*cdcd52d4SBartosz Sobczak irdma_debug_buf(dev, IRDMA_DEBUG_HMC, "COMMIT FPM BUFFER", 4550*cdcd52d4SBartosz Sobczak commit_fpm_mem.va, IRDMA_COMMIT_FPM_BUF_SIZE); 4551*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_commit_fpm_val(dev->cqp, 0, hmc_info->hmc_fn_id, 4552*cdcd52d4SBartosz Sobczak &commit_fpm_mem, true, wait_type); 4553*cdcd52d4SBartosz Sobczak if (!ret_code) 4554*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_parse_fpm_commit_buf(dev, dev->fpm_commit_buf, 4555*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj, 4556*cdcd52d4SBartosz Sobczak &hmc_info->sd_table.sd_cnt); 4557*cdcd52d4SBartosz Sobczak irdma_debug_buf(dev, IRDMA_DEBUG_HMC, "COMMIT FPM BUFFER", 4558*cdcd52d4SBartosz Sobczak commit_fpm_mem.va, IRDMA_COMMIT_FPM_BUF_SIZE); 4559*cdcd52d4SBartosz Sobczak 4560*cdcd52d4SBartosz Sobczak return ret_code; 4561*cdcd52d4SBartosz Sobczak } 4562*cdcd52d4SBartosz Sobczak 4563*cdcd52d4SBartosz Sobczak /** 4564*cdcd52d4SBartosz Sobczak * cqp_sds_wqe_fill - fill cqp wqe doe sd 4565*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 4566*cdcd52d4SBartosz Sobczak * @info: sd info for wqe 4567*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 4568*cdcd52d4SBartosz Sobczak */ 4569*cdcd52d4SBartosz Sobczak static int 4570*cdcd52d4SBartosz Sobczak cqp_sds_wqe_fill(struct irdma_sc_cqp *cqp, 4571*cdcd52d4SBartosz Sobczak struct irdma_update_sds_info *info, u64 scratch) 4572*cdcd52d4SBartosz Sobczak { 4573*cdcd52d4SBartosz Sobczak u64 data; 4574*cdcd52d4SBartosz Sobczak u64 hdr; 4575*cdcd52d4SBartosz Sobczak __le64 *wqe; 4576*cdcd52d4SBartosz Sobczak int mem_entries, wqe_entries; 4577*cdcd52d4SBartosz Sobczak struct irdma_dma_mem *sdbuf = &cqp->sdbuf; 4578*cdcd52d4SBartosz Sobczak u64 offset = 0; 4579*cdcd52d4SBartosz Sobczak u32 wqe_idx; 4580*cdcd52d4SBartosz Sobczak 4581*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe_idx(cqp, scratch, &wqe_idx); 4582*cdcd52d4SBartosz Sobczak if (!wqe) 4583*cdcd52d4SBartosz Sobczak return -ENOSPC; 4584*cdcd52d4SBartosz Sobczak 4585*cdcd52d4SBartosz Sobczak wqe_entries = (info->cnt > 3) ? 3 : info->cnt; 4586*cdcd52d4SBartosz Sobczak mem_entries = info->cnt - wqe_entries; 4587*cdcd52d4SBartosz Sobczak 4588*cdcd52d4SBartosz Sobczak if (mem_entries) { 4589*cdcd52d4SBartosz Sobczak offset = wqe_idx * IRDMA_UPDATE_SD_BUFF_SIZE; 4590*cdcd52d4SBartosz Sobczak irdma_memcpy(((char *)sdbuf->va + offset), &info->entry[3], mem_entries << 4); 4591*cdcd52d4SBartosz Sobczak 4592*cdcd52d4SBartosz Sobczak data = (u64)sdbuf->pa + offset; 4593*cdcd52d4SBartosz Sobczak } else { 4594*cdcd52d4SBartosz Sobczak data = 0; 4595*cdcd52d4SBartosz Sobczak } 4596*cdcd52d4SBartosz Sobczak data |= LS_64(info->hmc_fn_id, IRDMA_CQPSQ_UPESD_HMCFNID); 4597*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, data); 4598*cdcd52d4SBartosz Sobczak 4599*cdcd52d4SBartosz Sobczak switch (wqe_entries) { 4600*cdcd52d4SBartosz Sobczak case 3: 4601*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_48, 4602*cdcd52d4SBartosz Sobczak (LS_64(info->entry[2].cmd, IRDMA_CQPSQ_UPESD_SDCMD) | 4603*cdcd52d4SBartosz Sobczak LS_64(1, IRDMA_CQPSQ_UPESD_ENTRY_VALID))); 4604*cdcd52d4SBartosz Sobczak 4605*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_56, info->entry[2].data); 4606*cdcd52d4SBartosz Sobczak /* fallthrough */ 4607*cdcd52d4SBartosz Sobczak case 2: 4608*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, 4609*cdcd52d4SBartosz Sobczak (LS_64(info->entry[1].cmd, IRDMA_CQPSQ_UPESD_SDCMD) | 4610*cdcd52d4SBartosz Sobczak LS_64(1, IRDMA_CQPSQ_UPESD_ENTRY_VALID))); 4611*cdcd52d4SBartosz Sobczak 4612*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_40, info->entry[1].data); 4613*cdcd52d4SBartosz Sobczak /* fallthrough */ 4614*cdcd52d4SBartosz Sobczak case 1: 4615*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_0, 4616*cdcd52d4SBartosz Sobczak LS_64(info->entry[0].cmd, IRDMA_CQPSQ_UPESD_SDCMD)); 4617*cdcd52d4SBartosz Sobczak 4618*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_8, info->entry[0].data); 4619*cdcd52d4SBartosz Sobczak break; 4620*cdcd52d4SBartosz Sobczak default: 4621*cdcd52d4SBartosz Sobczak break; 4622*cdcd52d4SBartosz Sobczak } 4623*cdcd52d4SBartosz Sobczak 4624*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMA_CQP_OP_UPDATE_PE_SDS, IRDMA_CQPSQ_OPCODE) | 4625*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID) | 4626*cdcd52d4SBartosz Sobczak LS_64(mem_entries, IRDMA_CQPSQ_UPESD_ENTRY_COUNT); 4627*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 4628*cdcd52d4SBartosz Sobczak 4629*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 4630*cdcd52d4SBartosz Sobczak 4631*cdcd52d4SBartosz Sobczak if (mem_entries) 4632*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "UPDATE_PE_SDS WQE Buffer", 4633*cdcd52d4SBartosz Sobczak (char *)sdbuf->va + offset, mem_entries << 4); 4634*cdcd52d4SBartosz Sobczak 4635*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "UPDATE_PE_SDS WQE", wqe, 4636*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 4637*cdcd52d4SBartosz Sobczak 4638*cdcd52d4SBartosz Sobczak return 0; 4639*cdcd52d4SBartosz Sobczak } 4640*cdcd52d4SBartosz Sobczak 4641*cdcd52d4SBartosz Sobczak /** 4642*cdcd52d4SBartosz Sobczak * irdma_update_pe_sds - cqp wqe for sd 4643*cdcd52d4SBartosz Sobczak * @dev: ptr to irdma_dev struct 4644*cdcd52d4SBartosz Sobczak * @info: sd info for sd's 4645*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 4646*cdcd52d4SBartosz Sobczak */ 4647*cdcd52d4SBartosz Sobczak static int 4648*cdcd52d4SBartosz Sobczak irdma_update_pe_sds(struct irdma_sc_dev *dev, 4649*cdcd52d4SBartosz Sobczak struct irdma_update_sds_info *info, u64 scratch) 4650*cdcd52d4SBartosz Sobczak { 4651*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp = dev->cqp; 4652*cdcd52d4SBartosz Sobczak int ret_code; 4653*cdcd52d4SBartosz Sobczak 4654*cdcd52d4SBartosz Sobczak ret_code = cqp_sds_wqe_fill(cqp, info, scratch); 4655*cdcd52d4SBartosz Sobczak if (!ret_code) 4656*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 4657*cdcd52d4SBartosz Sobczak 4658*cdcd52d4SBartosz Sobczak return ret_code; 4659*cdcd52d4SBartosz Sobczak } 4660*cdcd52d4SBartosz Sobczak 4661*cdcd52d4SBartosz Sobczak /** 4662*cdcd52d4SBartosz Sobczak * irdma_update_sds_noccq - update sd before ccq created 4663*cdcd52d4SBartosz Sobczak * @dev: sc device struct 4664*cdcd52d4SBartosz Sobczak * @info: sd info for sd's 4665*cdcd52d4SBartosz Sobczak */ 4666*cdcd52d4SBartosz Sobczak int 4667*cdcd52d4SBartosz Sobczak irdma_update_sds_noccq(struct irdma_sc_dev *dev, 4668*cdcd52d4SBartosz Sobczak struct irdma_update_sds_info *info) 4669*cdcd52d4SBartosz Sobczak { 4670*cdcd52d4SBartosz Sobczak u32 error, val, tail; 4671*cdcd52d4SBartosz Sobczak struct irdma_sc_cqp *cqp = dev->cqp; 4672*cdcd52d4SBartosz Sobczak int ret_code; 4673*cdcd52d4SBartosz Sobczak 4674*cdcd52d4SBartosz Sobczak ret_code = cqp_sds_wqe_fill(cqp, info, 0); 4675*cdcd52d4SBartosz Sobczak if (ret_code) 4676*cdcd52d4SBartosz Sobczak return ret_code; 4677*cdcd52d4SBartosz Sobczak 4678*cdcd52d4SBartosz Sobczak irdma_get_cqp_reg_info(cqp, &val, &tail, &error); 4679*cdcd52d4SBartosz Sobczak 4680*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 4681*cdcd52d4SBartosz Sobczak return irdma_cqp_poll_registers(cqp, tail, 4682*cdcd52d4SBartosz Sobczak cqp->dev->hw_attrs.max_done_count); 4683*cdcd52d4SBartosz Sobczak } 4684*cdcd52d4SBartosz Sobczak 4685*cdcd52d4SBartosz Sobczak /** 4686*cdcd52d4SBartosz Sobczak * irdma_sc_static_hmc_pages_allocated - cqp wqe to allocate hmc pages 4687*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 4688*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 4689*cdcd52d4SBartosz Sobczak * @hmc_fn_id: hmc function id 4690*cdcd52d4SBartosz Sobczak * @post_sq: flag for cqp db to ring 4691*cdcd52d4SBartosz Sobczak * @poll_registers: flag to poll register for cqp completion 4692*cdcd52d4SBartosz Sobczak */ 4693*cdcd52d4SBartosz Sobczak int 4694*cdcd52d4SBartosz Sobczak irdma_sc_static_hmc_pages_allocated(struct irdma_sc_cqp *cqp, u64 scratch, 4695*cdcd52d4SBartosz Sobczak u8 hmc_fn_id, bool post_sq, 4696*cdcd52d4SBartosz Sobczak bool poll_registers) 4697*cdcd52d4SBartosz Sobczak { 4698*cdcd52d4SBartosz Sobczak u64 hdr; 4699*cdcd52d4SBartosz Sobczak __le64 *wqe; 4700*cdcd52d4SBartosz Sobczak u32 tail, val, error; 4701*cdcd52d4SBartosz Sobczak 4702*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 4703*cdcd52d4SBartosz Sobczak if (!wqe) 4704*cdcd52d4SBartosz Sobczak return -ENOSPC; 4705*cdcd52d4SBartosz Sobczak 4706*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_16, 4707*cdcd52d4SBartosz Sobczak LS_64(hmc_fn_id, IRDMA_SHMC_PAGE_ALLOCATED_HMC_FN_ID)); 4708*cdcd52d4SBartosz Sobczak 4709*cdcd52d4SBartosz Sobczak hdr = LS_64(IRDMA_CQP_OP_SHMC_PAGES_ALLOCATED, IRDMA_CQPSQ_OPCODE) | 4710*cdcd52d4SBartosz Sobczak LS_64(cqp->polarity, IRDMA_CQPSQ_WQEVALID); 4711*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 4712*cdcd52d4SBartosz Sobczak 4713*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, hdr); 4714*cdcd52d4SBartosz Sobczak 4715*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "SHMC_PAGES_ALLOCATED WQE", 4716*cdcd52d4SBartosz Sobczak wqe, IRDMA_CQP_WQE_SIZE * 8); 4717*cdcd52d4SBartosz Sobczak irdma_get_cqp_reg_info(cqp, &val, &tail, &error); 4718*cdcd52d4SBartosz Sobczak 4719*cdcd52d4SBartosz Sobczak if (post_sq) { 4720*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 4721*cdcd52d4SBartosz Sobczak if (poll_registers) 4722*cdcd52d4SBartosz Sobczak /* check for cqp sq tail update */ 4723*cdcd52d4SBartosz Sobczak return irdma_cqp_poll_registers(cqp, tail, 4724*cdcd52d4SBartosz Sobczak cqp->dev->hw_attrs.max_done_count); 4725*cdcd52d4SBartosz Sobczak else 4726*cdcd52d4SBartosz Sobczak return irdma_sc_poll_for_cqp_op_done(cqp, 4727*cdcd52d4SBartosz Sobczak IRDMA_CQP_OP_SHMC_PAGES_ALLOCATED, 4728*cdcd52d4SBartosz Sobczak NULL); 4729*cdcd52d4SBartosz Sobczak } 4730*cdcd52d4SBartosz Sobczak 4731*cdcd52d4SBartosz Sobczak return 0; 4732*cdcd52d4SBartosz Sobczak } 4733*cdcd52d4SBartosz Sobczak 4734*cdcd52d4SBartosz Sobczak /** 4735*cdcd52d4SBartosz Sobczak * irdma_cqp_ring_full - check if cqp ring is full 4736*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 4737*cdcd52d4SBartosz Sobczak */ 4738*cdcd52d4SBartosz Sobczak static bool 4739*cdcd52d4SBartosz Sobczak irdma_cqp_ring_full(struct irdma_sc_cqp *cqp) 4740*cdcd52d4SBartosz Sobczak { 4741*cdcd52d4SBartosz Sobczak return IRDMA_RING_FULL_ERR(cqp->sq_ring); 4742*cdcd52d4SBartosz Sobczak } 4743*cdcd52d4SBartosz Sobczak 4744*cdcd52d4SBartosz Sobczak /** 4745*cdcd52d4SBartosz Sobczak * irdma_est_sd - returns approximate number of SDs for HMC 4746*cdcd52d4SBartosz Sobczak * @dev: sc device struct 4747*cdcd52d4SBartosz Sobczak * @hmc_info: hmc structure, size and count for HMC objects 4748*cdcd52d4SBartosz Sobczak */ 4749*cdcd52d4SBartosz Sobczak static u32 irdma_est_sd(struct irdma_sc_dev *dev, 4750*cdcd52d4SBartosz Sobczak struct irdma_hmc_info *hmc_info){ 4751*cdcd52d4SBartosz Sobczak int i; 4752*cdcd52d4SBartosz Sobczak u64 size = 0; 4753*cdcd52d4SBartosz Sobczak u64 sd; 4754*cdcd52d4SBartosz Sobczak 4755*cdcd52d4SBartosz Sobczak for (i = IRDMA_HMC_IW_QP; i < IRDMA_HMC_IW_MAX; i++) 4756*cdcd52d4SBartosz Sobczak if (i != IRDMA_HMC_IW_PBLE) 4757*cdcd52d4SBartosz Sobczak size += round_up(hmc_info->hmc_obj[i].cnt * 4758*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[i].size, 512); 4759*cdcd52d4SBartosz Sobczak size += round_up(hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].cnt * 4760*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].size, 512); 4761*cdcd52d4SBartosz Sobczak if (size & 0x1FFFFF) 4762*cdcd52d4SBartosz Sobczak sd = (size >> 21) + 1; /* add 1 for remainder */ 4763*cdcd52d4SBartosz Sobczak else 4764*cdcd52d4SBartosz Sobczak sd = size >> 21; 4765*cdcd52d4SBartosz Sobczak if (sd > 0xFFFFFFFF) { 4766*cdcd52d4SBartosz Sobczak irdma_debug(dev, IRDMA_DEBUG_HMC, "sd overflow[%ld]\n", sd); 4767*cdcd52d4SBartosz Sobczak sd = 0xFFFFFFFF - 1; 4768*cdcd52d4SBartosz Sobczak } 4769*cdcd52d4SBartosz Sobczak 4770*cdcd52d4SBartosz Sobczak return (u32)sd; 4771*cdcd52d4SBartosz Sobczak } 4772*cdcd52d4SBartosz Sobczak 4773*cdcd52d4SBartosz Sobczak /** 4774*cdcd52d4SBartosz Sobczak * irdma_sc_query_rdma_features - query RDMA features and FW ver 4775*cdcd52d4SBartosz Sobczak * @cqp: struct for cqp hw 4776*cdcd52d4SBartosz Sobczak * @buf: buffer to hold query info 4777*cdcd52d4SBartosz Sobczak * @scratch: u64 saved to be used during cqp completion 4778*cdcd52d4SBartosz Sobczak */ 4779*cdcd52d4SBartosz Sobczak static int 4780*cdcd52d4SBartosz Sobczak irdma_sc_query_rdma_features(struct irdma_sc_cqp *cqp, 4781*cdcd52d4SBartosz Sobczak struct irdma_dma_mem *buf, u64 scratch) 4782*cdcd52d4SBartosz Sobczak { 4783*cdcd52d4SBartosz Sobczak __le64 *wqe; 4784*cdcd52d4SBartosz Sobczak u64 temp; 4785*cdcd52d4SBartosz Sobczak u32 tail, val, error; 4786*cdcd52d4SBartosz Sobczak int status; 4787*cdcd52d4SBartosz Sobczak 4788*cdcd52d4SBartosz Sobczak wqe = irdma_sc_cqp_get_next_send_wqe(cqp, scratch); 4789*cdcd52d4SBartosz Sobczak if (!wqe) 4790*cdcd52d4SBartosz Sobczak return -ENOSPC; 4791*cdcd52d4SBartosz Sobczak 4792*cdcd52d4SBartosz Sobczak temp = buf->pa; 4793*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_32, temp); 4794*cdcd52d4SBartosz Sobczak 4795*cdcd52d4SBartosz Sobczak temp = LS_64(cqp->polarity, IRDMA_CQPSQ_QUERY_RDMA_FEATURES_WQEVALID) | 4796*cdcd52d4SBartosz Sobczak LS_64(buf->size, IRDMA_CQPSQ_QUERY_RDMA_FEATURES_BUF_LEN) | 4797*cdcd52d4SBartosz Sobczak LS_64(IRDMA_CQP_OP_QUERY_RDMA_FEATURES, IRDMA_CQPSQ_UP_OP); 4798*cdcd52d4SBartosz Sobczak irdma_wmb(); /* make sure WQE is written before valid bit is set */ 4799*cdcd52d4SBartosz Sobczak 4800*cdcd52d4SBartosz Sobczak set_64bit_val(wqe, IRDMA_BYTE_24, temp); 4801*cdcd52d4SBartosz Sobczak 4802*cdcd52d4SBartosz Sobczak irdma_debug_buf(cqp->dev, IRDMA_DEBUG_WQE, "QUERY RDMA FEATURES", wqe, 4803*cdcd52d4SBartosz Sobczak IRDMA_CQP_WQE_SIZE * 8); 4804*cdcd52d4SBartosz Sobczak irdma_get_cqp_reg_info(cqp, &val, &tail, &error); 4805*cdcd52d4SBartosz Sobczak 4806*cdcd52d4SBartosz Sobczak irdma_sc_cqp_post_sq(cqp); 4807*cdcd52d4SBartosz Sobczak status = irdma_cqp_poll_registers(cqp, tail, 4808*cdcd52d4SBartosz Sobczak cqp->dev->hw_attrs.max_done_count); 4809*cdcd52d4SBartosz Sobczak if (error || status) 4810*cdcd52d4SBartosz Sobczak status = -EIO; 4811*cdcd52d4SBartosz Sobczak 4812*cdcd52d4SBartosz Sobczak return status; 4813*cdcd52d4SBartosz Sobczak } 4814*cdcd52d4SBartosz Sobczak 4815*cdcd52d4SBartosz Sobczak /** 4816*cdcd52d4SBartosz Sobczak * irdma_get_rdma_features - get RDMA features 4817*cdcd52d4SBartosz Sobczak * @dev: sc device struct 4818*cdcd52d4SBartosz Sobczak */ 4819*cdcd52d4SBartosz Sobczak int 4820*cdcd52d4SBartosz Sobczak irdma_get_rdma_features(struct irdma_sc_dev *dev) 4821*cdcd52d4SBartosz Sobczak { 4822*cdcd52d4SBartosz Sobczak int ret_code; 4823*cdcd52d4SBartosz Sobczak struct irdma_dma_mem feat_buf; 4824*cdcd52d4SBartosz Sobczak u64 temp; 4825*cdcd52d4SBartosz Sobczak u16 byte_idx, feat_type, feat_cnt, feat_idx; 4826*cdcd52d4SBartosz Sobczak 4827*cdcd52d4SBartosz Sobczak feat_buf.size = IRDMA_FEATURE_BUF_SIZE; 4828*cdcd52d4SBartosz Sobczak feat_buf.va = irdma_allocate_dma_mem(dev->hw, &feat_buf, feat_buf.size, 4829*cdcd52d4SBartosz Sobczak IRDMA_FEATURE_BUF_ALIGNMENT); 4830*cdcd52d4SBartosz Sobczak if (!feat_buf.va) 4831*cdcd52d4SBartosz Sobczak return -ENOMEM; 4832*cdcd52d4SBartosz Sobczak 4833*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_query_rdma_features(dev->cqp, &feat_buf, 0); 4834*cdcd52d4SBartosz Sobczak if (ret_code) 4835*cdcd52d4SBartosz Sobczak goto exit; 4836*cdcd52d4SBartosz Sobczak 4837*cdcd52d4SBartosz Sobczak get_64bit_val(feat_buf.va, IRDMA_BYTE_0, &temp); 4838*cdcd52d4SBartosz Sobczak feat_cnt = (u16)RS_64(temp, IRDMA_FEATURE_CNT); 4839*cdcd52d4SBartosz Sobczak if (feat_cnt < IRDMA_MIN_FEATURES) { 4840*cdcd52d4SBartosz Sobczak ret_code = -EINVAL; 4841*cdcd52d4SBartosz Sobczak goto exit; 4842*cdcd52d4SBartosz Sobczak } else if (feat_cnt > IRDMA_MAX_FEATURES) { 4843*cdcd52d4SBartosz Sobczak irdma_debug(dev, IRDMA_DEBUG_DEV, 4844*cdcd52d4SBartosz Sobczak "feature buf size insufficient," 4845*cdcd52d4SBartosz Sobczak "retrying with larger buffer\n"); 4846*cdcd52d4SBartosz Sobczak irdma_free_dma_mem(dev->hw, &feat_buf); 4847*cdcd52d4SBartosz Sobczak feat_buf.size = 8 * feat_cnt; 4848*cdcd52d4SBartosz Sobczak feat_buf.va = irdma_allocate_dma_mem(dev->hw, &feat_buf, 4849*cdcd52d4SBartosz Sobczak feat_buf.size, 4850*cdcd52d4SBartosz Sobczak IRDMA_FEATURE_BUF_ALIGNMENT); 4851*cdcd52d4SBartosz Sobczak if (!feat_buf.va) 4852*cdcd52d4SBartosz Sobczak return -ENOMEM; 4853*cdcd52d4SBartosz Sobczak 4854*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_query_rdma_features(dev->cqp, &feat_buf, 0); 4855*cdcd52d4SBartosz Sobczak if (ret_code) 4856*cdcd52d4SBartosz Sobczak goto exit; 4857*cdcd52d4SBartosz Sobczak 4858*cdcd52d4SBartosz Sobczak get_64bit_val(feat_buf.va, IRDMA_BYTE_0, &temp); 4859*cdcd52d4SBartosz Sobczak feat_cnt = (u16)RS_64(temp, IRDMA_FEATURE_CNT); 4860*cdcd52d4SBartosz Sobczak if (feat_cnt < IRDMA_MIN_FEATURES) { 4861*cdcd52d4SBartosz Sobczak ret_code = -EINVAL; 4862*cdcd52d4SBartosz Sobczak goto exit; 4863*cdcd52d4SBartosz Sobczak } 4864*cdcd52d4SBartosz Sobczak } 4865*cdcd52d4SBartosz Sobczak 4866*cdcd52d4SBartosz Sobczak irdma_debug_buf(dev, IRDMA_DEBUG_WQE, "QUERY RDMA FEATURES", feat_buf.va, 4867*cdcd52d4SBartosz Sobczak feat_cnt * 8); 4868*cdcd52d4SBartosz Sobczak 4869*cdcd52d4SBartosz Sobczak for (byte_idx = 0, feat_idx = 0; feat_idx < min(feat_cnt, (u16)IRDMA_MAX_FEATURES); 4870*cdcd52d4SBartosz Sobczak feat_idx++, byte_idx += 8) { 4871*cdcd52d4SBartosz Sobczak get_64bit_val(feat_buf.va, byte_idx, &temp); 4872*cdcd52d4SBartosz Sobczak feat_type = RS_64(temp, IRDMA_FEATURE_TYPE); 4873*cdcd52d4SBartosz Sobczak dev->feature_info[feat_type] = temp; 4874*cdcd52d4SBartosz Sobczak } 4875*cdcd52d4SBartosz Sobczak exit: 4876*cdcd52d4SBartosz Sobczak irdma_free_dma_mem(dev->hw, &feat_buf); 4877*cdcd52d4SBartosz Sobczak return ret_code; 4878*cdcd52d4SBartosz Sobczak } 4879*cdcd52d4SBartosz Sobczak 4880*cdcd52d4SBartosz Sobczak static u32 irdma_q1_cnt(struct irdma_sc_dev *dev, 4881*cdcd52d4SBartosz Sobczak struct irdma_hmc_info *hmc_info, u32 qpwanted){ 4882*cdcd52d4SBartosz Sobczak u32 q1_cnt; 4883*cdcd52d4SBartosz Sobczak 4884*cdcd52d4SBartosz Sobczak if (dev->hw_attrs.uk_attrs.hw_rev == IRDMA_GEN_1) { 4885*cdcd52d4SBartosz Sobczak q1_cnt = roundup_pow_of_two(dev->hw_attrs.max_hw_ird * 2 * qpwanted); 4886*cdcd52d4SBartosz Sobczak } else { 4887*cdcd52d4SBartosz Sobczak if (dev->cqp->protocol_used != IRDMA_IWARP_PROTOCOL_ONLY) 4888*cdcd52d4SBartosz Sobczak q1_cnt = roundup_pow_of_two(dev->hw_attrs.max_hw_ird * 2 * qpwanted + 512); 4889*cdcd52d4SBartosz Sobczak else 4890*cdcd52d4SBartosz Sobczak q1_cnt = dev->hw_attrs.max_hw_ird * 2 * qpwanted; 4891*cdcd52d4SBartosz Sobczak } 4892*cdcd52d4SBartosz Sobczak 4893*cdcd52d4SBartosz Sobczak return q1_cnt; 4894*cdcd52d4SBartosz Sobczak } 4895*cdcd52d4SBartosz Sobczak 4896*cdcd52d4SBartosz Sobczak static void 4897*cdcd52d4SBartosz Sobczak cfg_fpm_value_gen_1(struct irdma_sc_dev *dev, 4898*cdcd52d4SBartosz Sobczak struct irdma_hmc_info *hmc_info, u32 qpwanted) 4899*cdcd52d4SBartosz Sobczak { 4900*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_XF].cnt = roundup_pow_of_two(qpwanted * dev->hw_attrs.max_hw_wqes); 4901*cdcd52d4SBartosz Sobczak } 4902*cdcd52d4SBartosz Sobczak 4903*cdcd52d4SBartosz Sobczak static void 4904*cdcd52d4SBartosz Sobczak cfg_fpm_value_gen_2(struct irdma_sc_dev *dev, 4905*cdcd52d4SBartosz Sobczak struct irdma_hmc_info *hmc_info, u32 qpwanted) 4906*cdcd52d4SBartosz Sobczak { 4907*cdcd52d4SBartosz Sobczak struct irdma_hmc_fpm_misc *hmc_fpm_misc = &dev->hmc_fpm_misc; 4908*cdcd52d4SBartosz Sobczak 4909*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_XF].cnt = 4910*cdcd52d4SBartosz Sobczak 4 * hmc_fpm_misc->xf_block_size * qpwanted; 4911*cdcd52d4SBartosz Sobczak 4912*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_HDR].cnt = qpwanted; 4913*cdcd52d4SBartosz Sobczak 4914*cdcd52d4SBartosz Sobczak if (hmc_info->hmc_obj[IRDMA_HMC_IW_RRF].max_cnt) 4915*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_RRF].cnt = 32 * qpwanted; 4916*cdcd52d4SBartosz Sobczak if (hmc_info->hmc_obj[IRDMA_HMC_IW_RRFFL].max_cnt) 4917*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_RRFFL].cnt = 4918*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_RRF].cnt / 4919*cdcd52d4SBartosz Sobczak hmc_fpm_misc->rrf_block_size; 4920*cdcd52d4SBartosz Sobczak if (hmc_info->hmc_obj[IRDMA_HMC_IW_OOISC].max_cnt) 4921*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_OOISC].cnt = 32 * qpwanted; 4922*cdcd52d4SBartosz Sobczak if (hmc_info->hmc_obj[IRDMA_HMC_IW_OOISCFFL].max_cnt) 4923*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_OOISCFFL].cnt = 4924*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_OOISC].cnt / 4925*cdcd52d4SBartosz Sobczak hmc_fpm_misc->ooiscf_block_size; 4926*cdcd52d4SBartosz Sobczak } 4927*cdcd52d4SBartosz Sobczak 4928*cdcd52d4SBartosz Sobczak /** 4929*cdcd52d4SBartosz Sobczak * irdma_cfg_fpm_val - configure HMC objects 4930*cdcd52d4SBartosz Sobczak * @dev: sc device struct 4931*cdcd52d4SBartosz Sobczak * @qp_count: desired qp count 4932*cdcd52d4SBartosz Sobczak */ 4933*cdcd52d4SBartosz Sobczak int 4934*cdcd52d4SBartosz Sobczak irdma_cfg_fpm_val(struct irdma_sc_dev *dev, u32 qp_count) 4935*cdcd52d4SBartosz Sobczak { 4936*cdcd52d4SBartosz Sobczak struct irdma_virt_mem virt_mem; 4937*cdcd52d4SBartosz Sobczak u32 i, mem_size; 4938*cdcd52d4SBartosz Sobczak u32 qpwanted, mrwanted, pblewanted; 4939*cdcd52d4SBartosz Sobczak u32 powerof2, hte; 4940*cdcd52d4SBartosz Sobczak u32 sd_needed; 4941*cdcd52d4SBartosz Sobczak u32 sd_diff; 4942*cdcd52d4SBartosz Sobczak u32 loop_count = 0; 4943*cdcd52d4SBartosz Sobczak struct irdma_hmc_info *hmc_info; 4944*cdcd52d4SBartosz Sobczak struct irdma_hmc_fpm_misc *hmc_fpm_misc; 4945*cdcd52d4SBartosz Sobczak int ret_code = 0; 4946*cdcd52d4SBartosz Sobczak u32 max_sds; 4947*cdcd52d4SBartosz Sobczak 4948*cdcd52d4SBartosz Sobczak hmc_info = dev->hmc_info; 4949*cdcd52d4SBartosz Sobczak hmc_fpm_misc = &dev->hmc_fpm_misc; 4950*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_init_iw_hmc(dev, dev->hmc_fn_id); 4951*cdcd52d4SBartosz Sobczak if (ret_code) { 4952*cdcd52d4SBartosz Sobczak irdma_debug(dev, IRDMA_DEBUG_HMC, 4953*cdcd52d4SBartosz Sobczak "irdma_sc_init_iw_hmc returned error_code = %d\n", 4954*cdcd52d4SBartosz Sobczak ret_code); 4955*cdcd52d4SBartosz Sobczak return ret_code; 4956*cdcd52d4SBartosz Sobczak } 4957*cdcd52d4SBartosz Sobczak 4958*cdcd52d4SBartosz Sobczak max_sds = hmc_fpm_misc->max_sds; 4959*cdcd52d4SBartosz Sobczak 4960*cdcd52d4SBartosz Sobczak for (i = IRDMA_HMC_IW_QP; i < IRDMA_HMC_IW_MAX; i++) 4961*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[i].cnt = hmc_info->hmc_obj[i].max_cnt; 4962*cdcd52d4SBartosz Sobczak 4963*cdcd52d4SBartosz Sobczak sd_needed = irdma_est_sd(dev, hmc_info); 4964*cdcd52d4SBartosz Sobczak irdma_debug(dev, IRDMA_DEBUG_HMC, "sd count %d where max sd is %d\n", 4965*cdcd52d4SBartosz Sobczak hmc_info->sd_table.sd_cnt, max_sds); 4966*cdcd52d4SBartosz Sobczak 4967*cdcd52d4SBartosz Sobczak qpwanted = min(qp_count, hmc_info->hmc_obj[IRDMA_HMC_IW_QP].max_cnt); 4968*cdcd52d4SBartosz Sobczak 4969*cdcd52d4SBartosz Sobczak powerof2 = 1; 4970*cdcd52d4SBartosz Sobczak while (powerof2 <= qpwanted) 4971*cdcd52d4SBartosz Sobczak powerof2 *= 2; 4972*cdcd52d4SBartosz Sobczak powerof2 /= 2; 4973*cdcd52d4SBartosz Sobczak qpwanted = powerof2; 4974*cdcd52d4SBartosz Sobczak 4975*cdcd52d4SBartosz Sobczak mrwanted = hmc_info->hmc_obj[IRDMA_HMC_IW_MR].max_cnt; 4976*cdcd52d4SBartosz Sobczak pblewanted = hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].max_cnt; 4977*cdcd52d4SBartosz Sobczak 4978*cdcd52d4SBartosz Sobczak irdma_debug(dev, IRDMA_DEBUG_HMC, 4979*cdcd52d4SBartosz Sobczak "req_qp=%d max_sd=%d, max_qp = %d, max_cq=%d, max_mr=%d, max_pble=%d, mc=%d, av=%d\n", 4980*cdcd52d4SBartosz Sobczak qp_count, max_sds, 4981*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_QP].max_cnt, 4982*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_CQ].max_cnt, 4983*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_MR].max_cnt, 4984*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].max_cnt, 4985*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_FSIMC].max_cnt, 4986*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_FSIAV].max_cnt); 4987*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_FSIMC].cnt = 4988*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_FSIMC].max_cnt; 4989*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_FSIAV].cnt = 4990*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_FSIAV].max_cnt; 4991*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_ARP].cnt = 4992*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_ARP].max_cnt; 4993*cdcd52d4SBartosz Sobczak 4994*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_APBVT_ENTRY].cnt = 1; 4995*cdcd52d4SBartosz Sobczak 4996*cdcd52d4SBartosz Sobczak while (irdma_q1_cnt(dev, hmc_info, qpwanted) > hmc_info->hmc_obj[IRDMA_HMC_IW_Q1].max_cnt) 4997*cdcd52d4SBartosz Sobczak qpwanted /= 2; 4998*cdcd52d4SBartosz Sobczak 4999*cdcd52d4SBartosz Sobczak if (dev->hw_attrs.uk_attrs.hw_rev == IRDMA_GEN_1) { 5000*cdcd52d4SBartosz Sobczak cfg_fpm_value_gen_1(dev, hmc_info, qpwanted); 5001*cdcd52d4SBartosz Sobczak while (hmc_info->hmc_obj[IRDMA_HMC_IW_XF].cnt > hmc_info->hmc_obj[IRDMA_HMC_IW_XF].max_cnt) { 5002*cdcd52d4SBartosz Sobczak qpwanted /= 2; 5003*cdcd52d4SBartosz Sobczak cfg_fpm_value_gen_1(dev, hmc_info, qpwanted); 5004*cdcd52d4SBartosz Sobczak } 5005*cdcd52d4SBartosz Sobczak } 5006*cdcd52d4SBartosz Sobczak 5007*cdcd52d4SBartosz Sobczak do { 5008*cdcd52d4SBartosz Sobczak ++loop_count; 5009*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_QP].cnt = qpwanted; 5010*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_CQ].cnt = 5011*cdcd52d4SBartosz Sobczak min(2 * qpwanted, hmc_info->hmc_obj[IRDMA_HMC_IW_CQ].cnt); 5012*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_RESERVED].cnt = 0; /* Reserved */ 5013*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_MR].cnt = mrwanted; 5014*cdcd52d4SBartosz Sobczak 5015*cdcd52d4SBartosz Sobczak hte = round_up(qpwanted + hmc_info->hmc_obj[IRDMA_HMC_IW_FSIMC].cnt, 512); 5016*cdcd52d4SBartosz Sobczak powerof2 = 1; 5017*cdcd52d4SBartosz Sobczak while (powerof2 < hte) 5018*cdcd52d4SBartosz Sobczak powerof2 *= 2; 5019*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_HTE].cnt = 5020*cdcd52d4SBartosz Sobczak powerof2 * hmc_fpm_misc->ht_multiplier; 5021*cdcd52d4SBartosz Sobczak if (dev->hw_attrs.uk_attrs.hw_rev == IRDMA_GEN_1) 5022*cdcd52d4SBartosz Sobczak cfg_fpm_value_gen_1(dev, hmc_info, qpwanted); 5023*cdcd52d4SBartosz Sobczak else 5024*cdcd52d4SBartosz Sobczak cfg_fpm_value_gen_2(dev, hmc_info, qpwanted); 5025*cdcd52d4SBartosz Sobczak 5026*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_Q1].cnt = irdma_q1_cnt(dev, hmc_info, qpwanted); 5027*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_XFFL].cnt = 5028*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_XF].cnt / hmc_fpm_misc->xf_block_size; 5029*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_Q1FL].cnt = 5030*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_Q1].cnt / hmc_fpm_misc->q1_block_size; 5031*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_TIMER].cnt = 5032*cdcd52d4SBartosz Sobczak (round_up(qpwanted, 512) / 512 + 1) * hmc_fpm_misc->timer_bucket; 5033*cdcd52d4SBartosz Sobczak 5034*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].cnt = pblewanted; 5035*cdcd52d4SBartosz Sobczak sd_needed = irdma_est_sd(dev, hmc_info); 5036*cdcd52d4SBartosz Sobczak irdma_debug(dev, IRDMA_DEBUG_HMC, 5037*cdcd52d4SBartosz Sobczak "sd_needed = %d, max_sds=%d, mrwanted=%d, pblewanted=%d qpwanted=%d\n", 5038*cdcd52d4SBartosz Sobczak sd_needed, max_sds, mrwanted, pblewanted, qpwanted); 5039*cdcd52d4SBartosz Sobczak 5040*cdcd52d4SBartosz Sobczak /* Do not reduce resources further. All objects fit with max SDs */ 5041*cdcd52d4SBartosz Sobczak if (sd_needed <= max_sds) 5042*cdcd52d4SBartosz Sobczak break; 5043*cdcd52d4SBartosz Sobczak 5044*cdcd52d4SBartosz Sobczak sd_diff = sd_needed - max_sds; 5045*cdcd52d4SBartosz Sobczak if (sd_diff > 128) { 5046*cdcd52d4SBartosz Sobczak if (!(loop_count % 2) && qpwanted > 128) { 5047*cdcd52d4SBartosz Sobczak qpwanted /= 2; 5048*cdcd52d4SBartosz Sobczak } else { 5049*cdcd52d4SBartosz Sobczak mrwanted /= 2; 5050*cdcd52d4SBartosz Sobczak pblewanted /= 2; 5051*cdcd52d4SBartosz Sobczak } 5052*cdcd52d4SBartosz Sobczak continue; 5053*cdcd52d4SBartosz Sobczak } 5054*cdcd52d4SBartosz Sobczak if (dev->cqp->hmc_profile != IRDMA_HMC_PROFILE_FAVOR_VF && 5055*cdcd52d4SBartosz Sobczak pblewanted > (512 * FPM_MULTIPLIER * sd_diff)) { 5056*cdcd52d4SBartosz Sobczak pblewanted -= 256 * FPM_MULTIPLIER * sd_diff; 5057*cdcd52d4SBartosz Sobczak continue; 5058*cdcd52d4SBartosz Sobczak } else if (pblewanted > (100 * FPM_MULTIPLIER)) { 5059*cdcd52d4SBartosz Sobczak pblewanted -= 10 * FPM_MULTIPLIER; 5060*cdcd52d4SBartosz Sobczak } else if (pblewanted > FPM_MULTIPLIER) { 5061*cdcd52d4SBartosz Sobczak pblewanted -= FPM_MULTIPLIER; 5062*cdcd52d4SBartosz Sobczak } else if (qpwanted <= 128) { 5063*cdcd52d4SBartosz Sobczak if (hmc_info->hmc_obj[IRDMA_HMC_IW_FSIMC].cnt > 256) 5064*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_FSIMC].cnt /= 2; 5065*cdcd52d4SBartosz Sobczak if (hmc_info->hmc_obj[IRDMA_HMC_IW_FSIAV].cnt > 256) 5066*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_FSIAV].cnt /= 2; 5067*cdcd52d4SBartosz Sobczak } 5068*cdcd52d4SBartosz Sobczak if (mrwanted > FPM_MULTIPLIER) 5069*cdcd52d4SBartosz Sobczak mrwanted -= FPM_MULTIPLIER; 5070*cdcd52d4SBartosz Sobczak if (!(loop_count % 10) && qpwanted > 128) { 5071*cdcd52d4SBartosz Sobczak qpwanted /= 2; 5072*cdcd52d4SBartosz Sobczak if (hmc_info->hmc_obj[IRDMA_HMC_IW_FSIAV].cnt > 256) 5073*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_FSIAV].cnt /= 2; 5074*cdcd52d4SBartosz Sobczak } 5075*cdcd52d4SBartosz Sobczak } while (loop_count < 2000); 5076*cdcd52d4SBartosz Sobczak 5077*cdcd52d4SBartosz Sobczak if (sd_needed > max_sds) { 5078*cdcd52d4SBartosz Sobczak irdma_debug(dev, IRDMA_DEBUG_HMC, 5079*cdcd52d4SBartosz Sobczak "cfg_fpm failed loop_cnt=%d, sd_needed=%d, max sd count %d\n", 5080*cdcd52d4SBartosz Sobczak loop_count, sd_needed, hmc_info->sd_table.sd_cnt); 5081*cdcd52d4SBartosz Sobczak return -EINVAL; 5082*cdcd52d4SBartosz Sobczak } 5083*cdcd52d4SBartosz Sobczak 5084*cdcd52d4SBartosz Sobczak if (loop_count > 1 && sd_needed < max_sds) { 5085*cdcd52d4SBartosz Sobczak pblewanted += (max_sds - sd_needed) * 256 * FPM_MULTIPLIER; 5086*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].cnt = pblewanted; 5087*cdcd52d4SBartosz Sobczak sd_needed = irdma_est_sd(dev, hmc_info); 5088*cdcd52d4SBartosz Sobczak } 5089*cdcd52d4SBartosz Sobczak 5090*cdcd52d4SBartosz Sobczak irdma_debug(dev, IRDMA_DEBUG_HMC, 5091*cdcd52d4SBartosz Sobczak "loop_cnt=%d, sd_needed=%d, qpcnt = %d, cqcnt=%d, mrcnt=%d, pblecnt=%d, mc=%d, ah=%d, max sd count %d, first sd index %d\n", 5092*cdcd52d4SBartosz Sobczak loop_count, sd_needed, 5093*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_QP].cnt, 5094*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_CQ].cnt, 5095*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_MR].cnt, 5096*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_PBLE].cnt, 5097*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_FSIMC].cnt, 5098*cdcd52d4SBartosz Sobczak hmc_info->hmc_obj[IRDMA_HMC_IW_FSIAV].cnt, 5099*cdcd52d4SBartosz Sobczak hmc_info->sd_table.sd_cnt, hmc_info->first_sd_index); 5100*cdcd52d4SBartosz Sobczak 5101*cdcd52d4SBartosz Sobczak ret_code = irdma_sc_cfg_iw_fpm(dev, dev->hmc_fn_id); 5102*cdcd52d4SBartosz Sobczak if (ret_code) { 5103*cdcd52d4SBartosz Sobczak irdma_debug(dev, IRDMA_DEBUG_HMC, 5104*cdcd52d4SBartosz Sobczak "cfg_iw_fpm returned error_code[x%08X]\n", 5105*cdcd52d4SBartosz Sobczak readl(dev->hw_regs[IRDMA_CQPERRCODES])); 5106*cdcd52d4SBartosz Sobczak return ret_code; 5107*cdcd52d4SBartosz Sobczak } 5108*cdcd52d4SBartosz Sobczak 5109*cdcd52d4SBartosz Sobczak mem_size = sizeof(struct irdma_hmc_sd_entry) * 5110*cdcd52d4SBartosz Sobczak (hmc_info->sd_table.sd_cnt + hmc_info->first_sd_index + 1); 5111*cdcd52d4SBartosz Sobczak virt_mem.size = mem_size; 5112*cdcd52d4SBartosz Sobczak virt_mem.va = kzalloc(virt_mem.size, GFP_ATOMIC); 5113*cdcd52d4SBartosz Sobczak if (!virt_mem.va) { 5114*cdcd52d4SBartosz Sobczak irdma_debug(dev, IRDMA_DEBUG_HMC, 5115*cdcd52d4SBartosz Sobczak "failed to allocate memory for sd_entry buffer\n"); 5116*cdcd52d4SBartosz Sobczak return -ENOMEM; 5117*cdcd52d4SBartosz Sobczak } 5118*cdcd52d4SBartosz Sobczak hmc_info->sd_table.sd_entry = virt_mem.va; 5119*cdcd52d4SBartosz Sobczak 5120*cdcd52d4SBartosz Sobczak return ret_code; 5121*cdcd52d4SBartosz Sobczak } 5122*cdcd52d4SBartosz Sobczak 5123*cdcd52d4SBartosz Sobczak /** 5124*cdcd52d4SBartosz Sobczak * irdma_exec_cqp_cmd - execute cqp cmd when wqe are available 5125*cdcd52d4SBartosz Sobczak * @dev: rdma device 5126*cdcd52d4SBartosz Sobczak * @pcmdinfo: cqp command info 5127*cdcd52d4SBartosz Sobczak */ 5128*cdcd52d4SBartosz Sobczak static int 5129*cdcd52d4SBartosz Sobczak irdma_exec_cqp_cmd(struct irdma_sc_dev *dev, 5130*cdcd52d4SBartosz Sobczak struct cqp_cmds_info *pcmdinfo) 5131*cdcd52d4SBartosz Sobczak { 5132*cdcd52d4SBartosz Sobczak int status; 5133*cdcd52d4SBartosz Sobczak struct irdma_dma_mem val_mem; 5134*cdcd52d4SBartosz Sobczak bool alloc = false; 5135*cdcd52d4SBartosz Sobczak 5136*cdcd52d4SBartosz Sobczak dev->cqp_cmd_stats[pcmdinfo->cqp_cmd]++; 5137*cdcd52d4SBartosz Sobczak switch (pcmdinfo->cqp_cmd) { 5138*cdcd52d4SBartosz Sobczak case IRDMA_OP_CEQ_DESTROY: 5139*cdcd52d4SBartosz Sobczak status = irdma_sc_ceq_destroy(pcmdinfo->in.u.ceq_destroy.ceq, 5140*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.ceq_destroy.scratch, 5141*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5142*cdcd52d4SBartosz Sobczak break; 5143*cdcd52d4SBartosz Sobczak case IRDMA_OP_AEQ_DESTROY: 5144*cdcd52d4SBartosz Sobczak status = irdma_sc_aeq_destroy(pcmdinfo->in.u.aeq_destroy.aeq, 5145*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.aeq_destroy.scratch, 5146*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5147*cdcd52d4SBartosz Sobczak 5148*cdcd52d4SBartosz Sobczak break; 5149*cdcd52d4SBartosz Sobczak case IRDMA_OP_CEQ_CREATE: 5150*cdcd52d4SBartosz Sobczak status = irdma_sc_ceq_create(pcmdinfo->in.u.ceq_create.ceq, 5151*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.ceq_create.scratch, 5152*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5153*cdcd52d4SBartosz Sobczak break; 5154*cdcd52d4SBartosz Sobczak case IRDMA_OP_AEQ_CREATE: 5155*cdcd52d4SBartosz Sobczak status = irdma_sc_aeq_create(pcmdinfo->in.u.aeq_create.aeq, 5156*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.aeq_create.scratch, 5157*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5158*cdcd52d4SBartosz Sobczak break; 5159*cdcd52d4SBartosz Sobczak case IRDMA_OP_QP_UPLOAD_CONTEXT: 5160*cdcd52d4SBartosz Sobczak status = irdma_sc_qp_upload_context(pcmdinfo->in.u.qp_upload_context.dev, 5161*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.qp_upload_context.info, 5162*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.qp_upload_context.scratch, 5163*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5164*cdcd52d4SBartosz Sobczak break; 5165*cdcd52d4SBartosz Sobczak case IRDMA_OP_CQ_CREATE: 5166*cdcd52d4SBartosz Sobczak status = irdma_sc_cq_create(pcmdinfo->in.u.cq_create.cq, 5167*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.cq_create.scratch, 5168*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.cq_create.check_overflow, 5169*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5170*cdcd52d4SBartosz Sobczak break; 5171*cdcd52d4SBartosz Sobczak case IRDMA_OP_CQ_MODIFY: 5172*cdcd52d4SBartosz Sobczak status = irdma_sc_cq_modify(pcmdinfo->in.u.cq_modify.cq, 5173*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.cq_modify.info, 5174*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.cq_modify.scratch, 5175*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5176*cdcd52d4SBartosz Sobczak break; 5177*cdcd52d4SBartosz Sobczak case IRDMA_OP_CQ_DESTROY: 5178*cdcd52d4SBartosz Sobczak status = irdma_sc_cq_destroy(pcmdinfo->in.u.cq_destroy.cq, 5179*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.cq_destroy.scratch, 5180*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5181*cdcd52d4SBartosz Sobczak break; 5182*cdcd52d4SBartosz Sobczak case IRDMA_OP_QP_FLUSH_WQES: 5183*cdcd52d4SBartosz Sobczak status = irdma_sc_qp_flush_wqes(pcmdinfo->in.u.qp_flush_wqes.qp, 5184*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.qp_flush_wqes.info, 5185*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.qp_flush_wqes.scratch, 5186*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5187*cdcd52d4SBartosz Sobczak break; 5188*cdcd52d4SBartosz Sobczak case IRDMA_OP_GEN_AE: 5189*cdcd52d4SBartosz Sobczak status = irdma_sc_gen_ae(pcmdinfo->in.u.gen_ae.qp, 5190*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.gen_ae.info, 5191*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.gen_ae.scratch, 5192*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5193*cdcd52d4SBartosz Sobczak break; 5194*cdcd52d4SBartosz Sobczak case IRDMA_OP_MANAGE_PUSH_PAGE: 5195*cdcd52d4SBartosz Sobczak status = irdma_sc_manage_push_page(pcmdinfo->in.u.manage_push_page.cqp, 5196*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.manage_push_page.info, 5197*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.manage_push_page.scratch, 5198*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5199*cdcd52d4SBartosz Sobczak break; 5200*cdcd52d4SBartosz Sobczak case IRDMA_OP_UPDATE_PE_SDS: 5201*cdcd52d4SBartosz Sobczak status = irdma_update_pe_sds(pcmdinfo->in.u.update_pe_sds.dev, 5202*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.update_pe_sds.info, 5203*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.update_pe_sds.scratch); 5204*cdcd52d4SBartosz Sobczak break; 5205*cdcd52d4SBartosz Sobczak case IRDMA_OP_MANAGE_HMC_PM_FUNC_TABLE: 5206*cdcd52d4SBartosz Sobczak /* switch to calling through the call table */ 5207*cdcd52d4SBartosz Sobczak status = 5208*cdcd52d4SBartosz Sobczak irdma_sc_manage_hmc_pm_func_table(pcmdinfo->in.u.manage_hmc_pm.dev->cqp, 5209*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.manage_hmc_pm.info, 5210*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.manage_hmc_pm.scratch, 5211*cdcd52d4SBartosz Sobczak true); 5212*cdcd52d4SBartosz Sobczak break; 5213*cdcd52d4SBartosz Sobczak case IRDMA_OP_SUSPEND: 5214*cdcd52d4SBartosz Sobczak status = irdma_sc_suspend_qp(pcmdinfo->in.u.suspend_resume.cqp, 5215*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.suspend_resume.qp, 5216*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.suspend_resume.scratch); 5217*cdcd52d4SBartosz Sobczak break; 5218*cdcd52d4SBartosz Sobczak case IRDMA_OP_RESUME: 5219*cdcd52d4SBartosz Sobczak status = irdma_sc_resume_qp(pcmdinfo->in.u.suspend_resume.cqp, 5220*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.suspend_resume.qp, 5221*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.suspend_resume.scratch); 5222*cdcd52d4SBartosz Sobczak break; 5223*cdcd52d4SBartosz Sobczak case IRDMA_OP_QUERY_FPM_VAL: 5224*cdcd52d4SBartosz Sobczak val_mem.pa = pcmdinfo->in.u.query_fpm_val.fpm_val_pa; 5225*cdcd52d4SBartosz Sobczak val_mem.va = pcmdinfo->in.u.query_fpm_val.fpm_val_va; 5226*cdcd52d4SBartosz Sobczak status = irdma_sc_query_fpm_val(pcmdinfo->in.u.query_fpm_val.cqp, 5227*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.query_fpm_val.scratch, 5228*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.query_fpm_val.hmc_fn_id, 5229*cdcd52d4SBartosz Sobczak &val_mem, true, IRDMA_CQP_WAIT_EVENT); 5230*cdcd52d4SBartosz Sobczak break; 5231*cdcd52d4SBartosz Sobczak case IRDMA_OP_COMMIT_FPM_VAL: 5232*cdcd52d4SBartosz Sobczak val_mem.pa = pcmdinfo->in.u.commit_fpm_val.fpm_val_pa; 5233*cdcd52d4SBartosz Sobczak val_mem.va = pcmdinfo->in.u.commit_fpm_val.fpm_val_va; 5234*cdcd52d4SBartosz Sobczak status = irdma_sc_commit_fpm_val(pcmdinfo->in.u.commit_fpm_val.cqp, 5235*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.commit_fpm_val.scratch, 5236*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.commit_fpm_val.hmc_fn_id, 5237*cdcd52d4SBartosz Sobczak &val_mem, 5238*cdcd52d4SBartosz Sobczak true, 5239*cdcd52d4SBartosz Sobczak IRDMA_CQP_WAIT_EVENT); 5240*cdcd52d4SBartosz Sobczak break; 5241*cdcd52d4SBartosz Sobczak case IRDMA_OP_STATS_ALLOCATE: 5242*cdcd52d4SBartosz Sobczak alloc = true; 5243*cdcd52d4SBartosz Sobczak /* fallthrough */ 5244*cdcd52d4SBartosz Sobczak case IRDMA_OP_STATS_FREE: 5245*cdcd52d4SBartosz Sobczak status = irdma_sc_manage_stats_inst(pcmdinfo->in.u.stats_manage.cqp, 5246*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.stats_manage.info, 5247*cdcd52d4SBartosz Sobczak alloc, 5248*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.stats_manage.scratch); 5249*cdcd52d4SBartosz Sobczak break; 5250*cdcd52d4SBartosz Sobczak case IRDMA_OP_STATS_GATHER: 5251*cdcd52d4SBartosz Sobczak status = irdma_sc_gather_stats(pcmdinfo->in.u.stats_gather.cqp, 5252*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.stats_gather.info, 5253*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.stats_gather.scratch); 5254*cdcd52d4SBartosz Sobczak break; 5255*cdcd52d4SBartosz Sobczak case IRDMA_OP_WS_MODIFY_NODE: 5256*cdcd52d4SBartosz Sobczak status = irdma_sc_manage_ws_node(pcmdinfo->in.u.ws_node.cqp, 5257*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.ws_node.info, 5258*cdcd52d4SBartosz Sobczak IRDMA_MODIFY_NODE, 5259*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.ws_node.scratch); 5260*cdcd52d4SBartosz Sobczak break; 5261*cdcd52d4SBartosz Sobczak case IRDMA_OP_WS_DELETE_NODE: 5262*cdcd52d4SBartosz Sobczak status = irdma_sc_manage_ws_node(pcmdinfo->in.u.ws_node.cqp, 5263*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.ws_node.info, 5264*cdcd52d4SBartosz Sobczak IRDMA_DEL_NODE, 5265*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.ws_node.scratch); 5266*cdcd52d4SBartosz Sobczak break; 5267*cdcd52d4SBartosz Sobczak case IRDMA_OP_WS_ADD_NODE: 5268*cdcd52d4SBartosz Sobczak status = irdma_sc_manage_ws_node(pcmdinfo->in.u.ws_node.cqp, 5269*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.ws_node.info, 5270*cdcd52d4SBartosz Sobczak IRDMA_ADD_NODE, 5271*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.ws_node.scratch); 5272*cdcd52d4SBartosz Sobczak break; 5273*cdcd52d4SBartosz Sobczak case IRDMA_OP_SET_UP_MAP: 5274*cdcd52d4SBartosz Sobczak status = irdma_sc_set_up_map(pcmdinfo->in.u.up_map.cqp, 5275*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.up_map.info, 5276*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.up_map.scratch); 5277*cdcd52d4SBartosz Sobczak break; 5278*cdcd52d4SBartosz Sobczak case IRDMA_OP_QUERY_RDMA_FEATURES: 5279*cdcd52d4SBartosz Sobczak status = irdma_sc_query_rdma_features(pcmdinfo->in.u.query_rdma.cqp, 5280*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.query_rdma.query_buff_mem, 5281*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.query_rdma.scratch); 5282*cdcd52d4SBartosz Sobczak break; 5283*cdcd52d4SBartosz Sobczak case IRDMA_OP_DELETE_ARP_CACHE_ENTRY: 5284*cdcd52d4SBartosz Sobczak status = irdma_sc_del_arp_cache_entry(pcmdinfo->in.u.del_arp_cache_entry.cqp, 5285*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.del_arp_cache_entry.scratch, 5286*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.del_arp_cache_entry.arp_index, 5287*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5288*cdcd52d4SBartosz Sobczak break; 5289*cdcd52d4SBartosz Sobczak case IRDMA_OP_MANAGE_APBVT_ENTRY: 5290*cdcd52d4SBartosz Sobczak status = irdma_sc_manage_apbvt_entry(pcmdinfo->in.u.manage_apbvt_entry.cqp, 5291*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.manage_apbvt_entry.info, 5292*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.manage_apbvt_entry.scratch, 5293*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5294*cdcd52d4SBartosz Sobczak break; 5295*cdcd52d4SBartosz Sobczak case IRDMA_OP_MANAGE_QHASH_TABLE_ENTRY: 5296*cdcd52d4SBartosz Sobczak status = irdma_sc_manage_qhash_table_entry(pcmdinfo->in.u.manage_qhash_table_entry.cqp, 5297*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.manage_qhash_table_entry.info, 5298*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.manage_qhash_table_entry.scratch, 5299*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5300*cdcd52d4SBartosz Sobczak break; 5301*cdcd52d4SBartosz Sobczak case IRDMA_OP_QP_MODIFY: 5302*cdcd52d4SBartosz Sobczak status = irdma_sc_qp_modify(pcmdinfo->in.u.qp_modify.qp, 5303*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.qp_modify.info, 5304*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.qp_modify.scratch, 5305*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5306*cdcd52d4SBartosz Sobczak break; 5307*cdcd52d4SBartosz Sobczak case IRDMA_OP_QP_CREATE: 5308*cdcd52d4SBartosz Sobczak status = irdma_sc_qp_create(pcmdinfo->in.u.qp_create.qp, 5309*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.qp_create.info, 5310*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.qp_create.scratch, 5311*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5312*cdcd52d4SBartosz Sobczak break; 5313*cdcd52d4SBartosz Sobczak case IRDMA_OP_QP_DESTROY: 5314*cdcd52d4SBartosz Sobczak status = irdma_sc_qp_destroy(pcmdinfo->in.u.qp_destroy.qp, 5315*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.qp_destroy.scratch, 5316*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.qp_destroy.remove_hash_idx, 5317*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.qp_destroy.ignore_mw_bnd, 5318*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5319*cdcd52d4SBartosz Sobczak break; 5320*cdcd52d4SBartosz Sobczak case IRDMA_OP_ALLOC_STAG: 5321*cdcd52d4SBartosz Sobczak status = irdma_sc_alloc_stag(pcmdinfo->in.u.alloc_stag.dev, 5322*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.alloc_stag.info, 5323*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.alloc_stag.scratch, 5324*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5325*cdcd52d4SBartosz Sobczak break; 5326*cdcd52d4SBartosz Sobczak case IRDMA_OP_MR_REG_NON_SHARED: 5327*cdcd52d4SBartosz Sobczak status = irdma_sc_mr_reg_non_shared(pcmdinfo->in.u.mr_reg_non_shared.dev, 5328*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.mr_reg_non_shared.info, 5329*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.mr_reg_non_shared.scratch, 5330*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5331*cdcd52d4SBartosz Sobczak break; 5332*cdcd52d4SBartosz Sobczak case IRDMA_OP_DEALLOC_STAG: 5333*cdcd52d4SBartosz Sobczak status = irdma_sc_dealloc_stag(pcmdinfo->in.u.dealloc_stag.dev, 5334*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.dealloc_stag.info, 5335*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.dealloc_stag.scratch, 5336*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5337*cdcd52d4SBartosz Sobczak break; 5338*cdcd52d4SBartosz Sobczak case IRDMA_OP_MW_ALLOC: 5339*cdcd52d4SBartosz Sobczak status = irdma_sc_mw_alloc(pcmdinfo->in.u.mw_alloc.dev, 5340*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.mw_alloc.info, 5341*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.mw_alloc.scratch, 5342*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5343*cdcd52d4SBartosz Sobczak break; 5344*cdcd52d4SBartosz Sobczak case IRDMA_OP_ADD_ARP_CACHE_ENTRY: 5345*cdcd52d4SBartosz Sobczak status = irdma_sc_add_arp_cache_entry(pcmdinfo->in.u.add_arp_cache_entry.cqp, 5346*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.add_arp_cache_entry.info, 5347*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.add_arp_cache_entry.scratch, 5348*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5349*cdcd52d4SBartosz Sobczak break; 5350*cdcd52d4SBartosz Sobczak case IRDMA_OP_ALLOC_LOCAL_MAC_ENTRY: 5351*cdcd52d4SBartosz Sobczak status = irdma_sc_alloc_local_mac_entry(pcmdinfo->in.u.alloc_local_mac_entry.cqp, 5352*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.alloc_local_mac_entry.scratch, 5353*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5354*cdcd52d4SBartosz Sobczak break; 5355*cdcd52d4SBartosz Sobczak case IRDMA_OP_ADD_LOCAL_MAC_ENTRY: 5356*cdcd52d4SBartosz Sobczak status = irdma_sc_add_local_mac_entry(pcmdinfo->in.u.add_local_mac_entry.cqp, 5357*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.add_local_mac_entry.info, 5358*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.add_local_mac_entry.scratch, 5359*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5360*cdcd52d4SBartosz Sobczak break; 5361*cdcd52d4SBartosz Sobczak case IRDMA_OP_DELETE_LOCAL_MAC_ENTRY: 5362*cdcd52d4SBartosz Sobczak status = irdma_sc_del_local_mac_entry(pcmdinfo->in.u.del_local_mac_entry.cqp, 5363*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.del_local_mac_entry.scratch, 5364*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.del_local_mac_entry.entry_idx, 5365*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.del_local_mac_entry.ignore_ref_count, 5366*cdcd52d4SBartosz Sobczak pcmdinfo->post_sq); 5367*cdcd52d4SBartosz Sobczak break; 5368*cdcd52d4SBartosz Sobczak case IRDMA_OP_AH_CREATE: 5369*cdcd52d4SBartosz Sobczak status = irdma_sc_create_ah(pcmdinfo->in.u.ah_create.cqp, 5370*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.ah_create.info, 5371*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.ah_create.scratch); 5372*cdcd52d4SBartosz Sobczak break; 5373*cdcd52d4SBartosz Sobczak case IRDMA_OP_AH_DESTROY: 5374*cdcd52d4SBartosz Sobczak status = irdma_sc_destroy_ah(pcmdinfo->in.u.ah_destroy.cqp, 5375*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.ah_destroy.info, 5376*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.ah_destroy.scratch); 5377*cdcd52d4SBartosz Sobczak break; 5378*cdcd52d4SBartosz Sobczak case IRDMA_OP_MC_CREATE: 5379*cdcd52d4SBartosz Sobczak status = irdma_sc_create_mcast_grp(pcmdinfo->in.u.mc_create.cqp, 5380*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.mc_create.info, 5381*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.mc_create.scratch); 5382*cdcd52d4SBartosz Sobczak break; 5383*cdcd52d4SBartosz Sobczak case IRDMA_OP_MC_DESTROY: 5384*cdcd52d4SBartosz Sobczak status = irdma_sc_destroy_mcast_grp(pcmdinfo->in.u.mc_destroy.cqp, 5385*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.mc_destroy.info, 5386*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.mc_destroy.scratch); 5387*cdcd52d4SBartosz Sobczak break; 5388*cdcd52d4SBartosz Sobczak case IRDMA_OP_MC_MODIFY: 5389*cdcd52d4SBartosz Sobczak status = irdma_sc_modify_mcast_grp(pcmdinfo->in.u.mc_modify.cqp, 5390*cdcd52d4SBartosz Sobczak &pcmdinfo->in.u.mc_modify.info, 5391*cdcd52d4SBartosz Sobczak pcmdinfo->in.u.mc_modify.scratch); 5392*cdcd52d4SBartosz Sobczak break; 5393*cdcd52d4SBartosz Sobczak default: 5394*cdcd52d4SBartosz Sobczak status = -EOPNOTSUPP; 5395*cdcd52d4SBartosz Sobczak break; 5396*cdcd52d4SBartosz Sobczak } 5397*cdcd52d4SBartosz Sobczak 5398*cdcd52d4SBartosz Sobczak return status; 5399*cdcd52d4SBartosz Sobczak } 5400*cdcd52d4SBartosz Sobczak 5401*cdcd52d4SBartosz Sobczak /** 5402*cdcd52d4SBartosz Sobczak * irdma_process_cqp_cmd - process all cqp commands 5403*cdcd52d4SBartosz Sobczak * @dev: sc device struct 5404*cdcd52d4SBartosz Sobczak * @pcmdinfo: cqp command info 5405*cdcd52d4SBartosz Sobczak */ 5406*cdcd52d4SBartosz Sobczak int 5407*cdcd52d4SBartosz Sobczak irdma_process_cqp_cmd(struct irdma_sc_dev *dev, 5408*cdcd52d4SBartosz Sobczak struct cqp_cmds_info *pcmdinfo) 5409*cdcd52d4SBartosz Sobczak { 5410*cdcd52d4SBartosz Sobczak int status = 0; 5411*cdcd52d4SBartosz Sobczak unsigned long flags; 5412*cdcd52d4SBartosz Sobczak 5413*cdcd52d4SBartosz Sobczak if (dev->no_cqp) 5414*cdcd52d4SBartosz Sobczak return -EFAULT; 5415*cdcd52d4SBartosz Sobczak 5416*cdcd52d4SBartosz Sobczak spin_lock_irqsave(&dev->cqp_lock, flags); 5417*cdcd52d4SBartosz Sobczak if (list_empty(&dev->cqp_cmd_head) && !irdma_cqp_ring_full(dev->cqp)) 5418*cdcd52d4SBartosz Sobczak status = irdma_exec_cqp_cmd(dev, pcmdinfo); 5419*cdcd52d4SBartosz Sobczak else 5420*cdcd52d4SBartosz Sobczak list_add_tail(&pcmdinfo->cqp_cmd_entry, &dev->cqp_cmd_head); 5421*cdcd52d4SBartosz Sobczak spin_unlock_irqrestore(&dev->cqp_lock, flags); 5422*cdcd52d4SBartosz Sobczak return status; 5423*cdcd52d4SBartosz Sobczak } 5424*cdcd52d4SBartosz Sobczak 5425*cdcd52d4SBartosz Sobczak /** 5426*cdcd52d4SBartosz Sobczak * irdma_process_bh - called from tasklet for cqp list 5427*cdcd52d4SBartosz Sobczak * @dev: sc device struct 5428*cdcd52d4SBartosz Sobczak */ 5429*cdcd52d4SBartosz Sobczak int 5430*cdcd52d4SBartosz Sobczak irdma_process_bh(struct irdma_sc_dev *dev) 5431*cdcd52d4SBartosz Sobczak { 5432*cdcd52d4SBartosz Sobczak int status = 0; 5433*cdcd52d4SBartosz Sobczak struct cqp_cmds_info *pcmdinfo; 5434*cdcd52d4SBartosz Sobczak unsigned long flags; 5435*cdcd52d4SBartosz Sobczak 5436*cdcd52d4SBartosz Sobczak spin_lock_irqsave(&dev->cqp_lock, flags); 5437*cdcd52d4SBartosz Sobczak while (!list_empty(&dev->cqp_cmd_head) && 5438*cdcd52d4SBartosz Sobczak !irdma_cqp_ring_full(dev->cqp)) { 5439*cdcd52d4SBartosz Sobczak pcmdinfo = (struct cqp_cmds_info *)irdma_remove_cqp_head(dev); 5440*cdcd52d4SBartosz Sobczak status = irdma_exec_cqp_cmd(dev, pcmdinfo); 5441*cdcd52d4SBartosz Sobczak if (status) 5442*cdcd52d4SBartosz Sobczak break; 5443*cdcd52d4SBartosz Sobczak } 5444*cdcd52d4SBartosz Sobczak spin_unlock_irqrestore(&dev->cqp_lock, flags); 5445*cdcd52d4SBartosz Sobczak return status; 5446*cdcd52d4SBartosz Sobczak } 5447*cdcd52d4SBartosz Sobczak 5448*cdcd52d4SBartosz Sobczak /** 5449*cdcd52d4SBartosz Sobczak * irdma_cfg_aeq- Configure AEQ interrupt 5450*cdcd52d4SBartosz Sobczak * @dev: pointer to the device structure 5451*cdcd52d4SBartosz Sobczak * @idx: vector index 5452*cdcd52d4SBartosz Sobczak * @enable: True to enable, False disables 5453*cdcd52d4SBartosz Sobczak */ 5454*cdcd52d4SBartosz Sobczak void 5455*cdcd52d4SBartosz Sobczak irdma_cfg_aeq(struct irdma_sc_dev *dev, u32 idx, bool enable) 5456*cdcd52d4SBartosz Sobczak { 5457*cdcd52d4SBartosz Sobczak u32 reg_val; 5458*cdcd52d4SBartosz Sobczak reg_val = enable ? IRDMA_PFINT_AEQCTL_CAUSE_ENA_M : 0; 5459*cdcd52d4SBartosz Sobczak reg_val |= (idx << IRDMA_PFINT_AEQCTL_MSIX_INDX_S) | 5460*cdcd52d4SBartosz Sobczak IRDMA_PFINT_AEQCTL_ITR_INDX_M; 5461*cdcd52d4SBartosz Sobczak writel(reg_val, dev->hw_regs[IRDMA_PFINT_AEQCTL]); 5462*cdcd52d4SBartosz Sobczak } 5463*cdcd52d4SBartosz Sobczak 5464*cdcd52d4SBartosz Sobczak /** 5465*cdcd52d4SBartosz Sobczak * sc_vsi_update_stats - Update statistics 5466*cdcd52d4SBartosz Sobczak * @vsi: sc_vsi instance to update 5467*cdcd52d4SBartosz Sobczak */ 5468*cdcd52d4SBartosz Sobczak void 5469*cdcd52d4SBartosz Sobczak sc_vsi_update_stats(struct irdma_sc_vsi *vsi) 5470*cdcd52d4SBartosz Sobczak { 5471*cdcd52d4SBartosz Sobczak struct irdma_gather_stats *gather_stats; 5472*cdcd52d4SBartosz Sobczak struct irdma_gather_stats *last_gather_stats; 5473*cdcd52d4SBartosz Sobczak 5474*cdcd52d4SBartosz Sobczak gather_stats = vsi->pestat->gather_info.gather_stats_va; 5475*cdcd52d4SBartosz Sobczak last_gather_stats = vsi->pestat->gather_info.last_gather_stats_va; 5476*cdcd52d4SBartosz Sobczak irdma_update_stats(&vsi->pestat->hw_stats, gather_stats, 5477*cdcd52d4SBartosz Sobczak last_gather_stats, vsi->dev->hw_stats_map, 5478*cdcd52d4SBartosz Sobczak vsi->dev->hw_attrs.max_stat_idx); 5479*cdcd52d4SBartosz Sobczak } 5480*cdcd52d4SBartosz Sobczak 5481*cdcd52d4SBartosz Sobczak /** 5482*cdcd52d4SBartosz Sobczak * irdma_wait_pe_ready - Check if firmware is ready 5483*cdcd52d4SBartosz Sobczak * @dev: provides access to registers 5484*cdcd52d4SBartosz Sobczak */ 5485*cdcd52d4SBartosz Sobczak static int 5486*cdcd52d4SBartosz Sobczak irdma_wait_pe_ready(struct irdma_sc_dev *dev) 5487*cdcd52d4SBartosz Sobczak { 5488*cdcd52d4SBartosz Sobczak u32 statuscpu0; 5489*cdcd52d4SBartosz Sobczak u32 statuscpu1; 5490*cdcd52d4SBartosz Sobczak u32 statuscpu2; 5491*cdcd52d4SBartosz Sobczak u32 retrycount = 0; 5492*cdcd52d4SBartosz Sobczak 5493*cdcd52d4SBartosz Sobczak do { 5494*cdcd52d4SBartosz Sobczak statuscpu0 = readl(dev->hw_regs[IRDMA_GLPE_CPUSTATUS0]); 5495*cdcd52d4SBartosz Sobczak statuscpu1 = readl(dev->hw_regs[IRDMA_GLPE_CPUSTATUS1]); 5496*cdcd52d4SBartosz Sobczak statuscpu2 = readl(dev->hw_regs[IRDMA_GLPE_CPUSTATUS2]); 5497*cdcd52d4SBartosz Sobczak if (statuscpu0 == 0x80 && statuscpu1 == 0x80 && 5498*cdcd52d4SBartosz Sobczak statuscpu2 == 0x80) 5499*cdcd52d4SBartosz Sobczak return 0; 5500*cdcd52d4SBartosz Sobczak mdelay(1000); 5501*cdcd52d4SBartosz Sobczak } while (retrycount++ < dev->hw_attrs.max_pe_ready_count); 5502*cdcd52d4SBartosz Sobczak return -1; 5503*cdcd52d4SBartosz Sobczak } 5504*cdcd52d4SBartosz Sobczak 5505*cdcd52d4SBartosz Sobczak static inline void 5506*cdcd52d4SBartosz Sobczak irdma_sc_init_hw(struct irdma_sc_dev *dev) 5507*cdcd52d4SBartosz Sobczak { 5508*cdcd52d4SBartosz Sobczak switch (dev->hw_attrs.uk_attrs.hw_rev) { 5509*cdcd52d4SBartosz Sobczak case IRDMA_GEN_2: 5510*cdcd52d4SBartosz Sobczak icrdma_init_hw(dev); 5511*cdcd52d4SBartosz Sobczak break; 5512*cdcd52d4SBartosz Sobczak } 5513*cdcd52d4SBartosz Sobczak } 5514*cdcd52d4SBartosz Sobczak 5515*cdcd52d4SBartosz Sobczak /** 5516*cdcd52d4SBartosz Sobczak * irdma_sc_dev_init - Initialize control part of device 5517*cdcd52d4SBartosz Sobczak * @ver: version 5518*cdcd52d4SBartosz Sobczak * @dev: Device pointer 5519*cdcd52d4SBartosz Sobczak * @info: Device init info 5520*cdcd52d4SBartosz Sobczak */ 5521*cdcd52d4SBartosz Sobczak int 5522*cdcd52d4SBartosz Sobczak irdma_sc_dev_init(enum irdma_vers ver, struct irdma_sc_dev *dev, 5523*cdcd52d4SBartosz Sobczak struct irdma_device_init_info *info) 5524*cdcd52d4SBartosz Sobczak { 5525*cdcd52d4SBartosz Sobczak u32 val; 5526*cdcd52d4SBartosz Sobczak int ret_code = 0; 5527*cdcd52d4SBartosz Sobczak u8 db_size; 5528*cdcd52d4SBartosz Sobczak 5529*cdcd52d4SBartosz Sobczak INIT_LIST_HEAD(&dev->cqp_cmd_head); /* for CQP command backlog */ 5530*cdcd52d4SBartosz Sobczak mutex_init(&dev->ws_mutex); 5531*cdcd52d4SBartosz Sobczak dev->debug_mask = info->debug_mask; 5532*cdcd52d4SBartosz Sobczak dev->hmc_fn_id = info->hmc_fn_id; 5533*cdcd52d4SBartosz Sobczak dev->fpm_query_buf_pa = info->fpm_query_buf_pa; 5534*cdcd52d4SBartosz Sobczak dev->fpm_query_buf = info->fpm_query_buf; 5535*cdcd52d4SBartosz Sobczak dev->fpm_commit_buf_pa = info->fpm_commit_buf_pa; 5536*cdcd52d4SBartosz Sobczak dev->fpm_commit_buf = info->fpm_commit_buf; 5537*cdcd52d4SBartosz Sobczak dev->hw = info->hw; 5538*cdcd52d4SBartosz Sobczak dev->hw->hw_addr = info->bar0; 5539*cdcd52d4SBartosz Sobczak /* Setup the hardware limits, hmc may limit further */ 5540*cdcd52d4SBartosz Sobczak dev->hw_attrs.min_hw_qp_id = IRDMA_MIN_IW_QP_ID; 5541*cdcd52d4SBartosz Sobczak dev->hw_attrs.min_hw_aeq_size = IRDMA_MIN_AEQ_ENTRIES; 5542*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_hw_aeq_size = IRDMA_MAX_AEQ_ENTRIES; 5543*cdcd52d4SBartosz Sobczak dev->hw_attrs.min_hw_ceq_size = IRDMA_MIN_CEQ_ENTRIES; 5544*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_hw_ceq_size = IRDMA_MAX_CEQ_ENTRIES; 5545*cdcd52d4SBartosz Sobczak dev->hw_attrs.uk_attrs.min_hw_cq_size = IRDMA_MIN_CQ_SIZE; 5546*cdcd52d4SBartosz Sobczak dev->hw_attrs.uk_attrs.max_hw_cq_size = IRDMA_MAX_CQ_SIZE; 5547*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_hw_outbound_msg_size = IRDMA_MAX_OUTBOUND_MSG_SIZE; 5548*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_mr_size = IRDMA_MAX_MR_SIZE; 5549*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_hw_inbound_msg_size = IRDMA_MAX_INBOUND_MSG_SIZE; 5550*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_hw_device_pages = IRDMA_MAX_PUSH_PAGE_COUNT; 5551*cdcd52d4SBartosz Sobczak dev->hw_attrs.uk_attrs.max_hw_inline = IRDMA_MAX_INLINE_DATA_SIZE; 5552*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_hw_wqes = IRDMA_MAX_WQ_ENTRIES; 5553*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_qp_wr = IRDMA_MAX_QP_WRS(IRDMA_MAX_QUANTA_PER_WR); 5554*cdcd52d4SBartosz Sobczak 5555*cdcd52d4SBartosz Sobczak dev->hw_attrs.uk_attrs.max_hw_rq_quanta = IRDMA_QP_SW_MAX_RQ_QUANTA; 5556*cdcd52d4SBartosz Sobczak dev->hw_attrs.uk_attrs.max_hw_wq_quanta = IRDMA_QP_SW_MAX_WQ_QUANTA; 5557*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_hw_pds = IRDMA_MAX_PDS; 5558*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_hw_ena_vf_count = IRDMA_MAX_PE_ENA_VF_COUNT; 5559*cdcd52d4SBartosz Sobczak 5560*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_pe_ready_count = 14; 5561*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_done_count = IRDMA_DONE_COUNT; 5562*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_sleep_count = IRDMA_SLEEP_COUNT; 5563*cdcd52d4SBartosz Sobczak dev->hw_attrs.max_cqp_compl_wait_time_ms = CQP_COMPL_WAIT_TIME_MS; 5564*cdcd52d4SBartosz Sobczak 5565*cdcd52d4SBartosz Sobczak dev->hw_attrs.uk_attrs.hw_rev = ver; 5566*cdcd52d4SBartosz Sobczak irdma_sc_init_hw(dev); 5567*cdcd52d4SBartosz Sobczak 5568*cdcd52d4SBartosz Sobczak if (irdma_wait_pe_ready(dev)) 5569*cdcd52d4SBartosz Sobczak return -ETIMEDOUT; 5570*cdcd52d4SBartosz Sobczak 5571*cdcd52d4SBartosz Sobczak val = readl(dev->hw_regs[IRDMA_GLPCI_LBARCTRL]); 5572*cdcd52d4SBartosz Sobczak db_size = (u8)RS_32(val, IRDMA_GLPCI_LBARCTRL_PE_DB_SIZE); 5573*cdcd52d4SBartosz Sobczak if (db_size != IRDMA_PE_DB_SIZE_4M && db_size != IRDMA_PE_DB_SIZE_8M) { 5574*cdcd52d4SBartosz Sobczak irdma_debug(dev, IRDMA_DEBUG_DEV, 5575*cdcd52d4SBartosz Sobczak "RDMA PE doorbell is not enabled in CSR val 0x%x db_size=%d\n", 5576*cdcd52d4SBartosz Sobczak val, db_size); 5577*cdcd52d4SBartosz Sobczak return -ENODEV; 5578*cdcd52d4SBartosz Sobczak } 5579*cdcd52d4SBartosz Sobczak dev->db_addr = dev->hw->hw_addr + (uintptr_t)dev->hw_regs[IRDMA_DB_ADDR_OFFSET]; 5580*cdcd52d4SBartosz Sobczak 5581*cdcd52d4SBartosz Sobczak return ret_code; 5582*cdcd52d4SBartosz Sobczak } 5583*cdcd52d4SBartosz Sobczak 5584*cdcd52d4SBartosz Sobczak /** 5585*cdcd52d4SBartosz Sobczak * irdma_stat_val - Extract HW counter value from statistics buffer 5586*cdcd52d4SBartosz Sobczak * @stats_val: pointer to statistics buffer 5587*cdcd52d4SBartosz Sobczak * @byteoff: byte offset of counter value in the buffer (8B-aligned) 5588*cdcd52d4SBartosz Sobczak * @bitoff: bit offset of counter value within 8B entry 5589*cdcd52d4SBartosz Sobczak * @bitmask: maximum counter value (e.g. 0xffffff for 24-bit counter) 5590*cdcd52d4SBartosz Sobczak */ 5591*cdcd52d4SBartosz Sobczak static inline u64 irdma_stat_val(const u64 *stats_val, u16 byteoff, 5592*cdcd52d4SBartosz Sobczak u8 bitoff, u64 bitmask){ 5593*cdcd52d4SBartosz Sobczak u16 idx = byteoff / sizeof(*stats_val); 5594*cdcd52d4SBartosz Sobczak 5595*cdcd52d4SBartosz Sobczak return (stats_val[idx] >> bitoff) & bitmask; 5596*cdcd52d4SBartosz Sobczak } 5597*cdcd52d4SBartosz Sobczak 5598*cdcd52d4SBartosz Sobczak /** 5599*cdcd52d4SBartosz Sobczak * irdma_stat_delta - Calculate counter delta 5600*cdcd52d4SBartosz Sobczak * @new_val: updated counter value 5601*cdcd52d4SBartosz Sobczak * @old_val: last counter value 5602*cdcd52d4SBartosz Sobczak * @max_val: maximum counter value (e.g. 0xffffff for 24-bit counter) 5603*cdcd52d4SBartosz Sobczak */ 5604*cdcd52d4SBartosz Sobczak static inline u64 irdma_stat_delta(u64 new_val, u64 old_val, u64 max_val) { 5605*cdcd52d4SBartosz Sobczak if (new_val >= old_val) 5606*cdcd52d4SBartosz Sobczak return new_val - old_val; 5607*cdcd52d4SBartosz Sobczak else 5608*cdcd52d4SBartosz Sobczak /* roll-over case */ 5609*cdcd52d4SBartosz Sobczak return max_val - old_val + new_val + 1; 5610*cdcd52d4SBartosz Sobczak } 5611*cdcd52d4SBartosz Sobczak 5612*cdcd52d4SBartosz Sobczak /** 5613*cdcd52d4SBartosz Sobczak * irdma_update_stats - Update statistics 5614*cdcd52d4SBartosz Sobczak * @hw_stats: hw_stats instance to update 5615*cdcd52d4SBartosz Sobczak * @gather_stats: updated stat counters 5616*cdcd52d4SBartosz Sobczak * @last_gather_stats: last stat counters 5617*cdcd52d4SBartosz Sobczak * @map: HW stat map (hw_stats => gather_stats) 5618*cdcd52d4SBartosz Sobczak * @max_stat_idx: number of HW stats 5619*cdcd52d4SBartosz Sobczak */ 5620*cdcd52d4SBartosz Sobczak void 5621*cdcd52d4SBartosz Sobczak irdma_update_stats(struct irdma_dev_hw_stats *hw_stats, 5622*cdcd52d4SBartosz Sobczak struct irdma_gather_stats *gather_stats, 5623*cdcd52d4SBartosz Sobczak struct irdma_gather_stats *last_gather_stats, 5624*cdcd52d4SBartosz Sobczak const struct irdma_hw_stat_map *map, 5625*cdcd52d4SBartosz Sobczak u16 max_stat_idx) 5626*cdcd52d4SBartosz Sobczak { 5627*cdcd52d4SBartosz Sobczak u64 *stats_val = hw_stats->stats_val; 5628*cdcd52d4SBartosz Sobczak u16 i; 5629*cdcd52d4SBartosz Sobczak 5630*cdcd52d4SBartosz Sobczak for (i = 0; i < max_stat_idx; i++) { 5631*cdcd52d4SBartosz Sobczak u64 new_val = irdma_stat_val(gather_stats->val, 5632*cdcd52d4SBartosz Sobczak map[i].byteoff, map[i].bitoff, 5633*cdcd52d4SBartosz Sobczak map[i].bitmask); 5634*cdcd52d4SBartosz Sobczak u64 last_val = irdma_stat_val(last_gather_stats->val, 5635*cdcd52d4SBartosz Sobczak map[i].byteoff, map[i].bitoff, 5636*cdcd52d4SBartosz Sobczak map[i].bitmask); 5637*cdcd52d4SBartosz Sobczak 5638*cdcd52d4SBartosz Sobczak stats_val[i] += irdma_stat_delta(new_val, last_val, 5639*cdcd52d4SBartosz Sobczak map[i].bitmask); 5640*cdcd52d4SBartosz Sobczak } 5641*cdcd52d4SBartosz Sobczak 5642*cdcd52d4SBartosz Sobczak irdma_memcpy(last_gather_stats, gather_stats, 5643*cdcd52d4SBartosz Sobczak sizeof(*last_gather_stats)); 5644*cdcd52d4SBartosz Sobczak } 5645