aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/ethernet/broadcom/bnx2x
diff options
context:
space:
mode:
authorYuval Mintz <Yuval.Mintz@qlogic.com>2014-12-04 05:52:06 -0500
committerDavid S. Miller <davem@davemloft.net>2014-12-09 14:29:10 -0500
commit02dc4025a088ea7ff53fcb35ba9e0f295078a4a0 (patch)
tree7e80c38e46064c840883a5d1e7176756954b3ebb /drivers/net/ethernet/broadcom/bnx2x
parent36c71a735ac2c7046ab1c234c734b2dd9035ad4f (diff)
bnx2x: Use correct fastpath version for VFs.
Our FW can support several fastpath HSI [for backward compatibility] but up until now VFs were always configured to use latest fastpath HSI [although VF driver might be older and use an older fastpath HSI]. For linux drivers, the differences are insignificant since driver never utilized features that were overridden by the HSI change. But for VMs running other operating systems this might be a problem. In addition, eventually FW might change fastpath HSI in such a manner that backward compatibility WILL break unless configured with proper version. This patch fixes the issue for other operating system VMs, as well as lays the ground work for forward compatibility in regard to the fastpath HSI. Signed-off-by: Yuval Mintz <Yuval.Mintz@qlogic.com> Signed-off-by: Ariel Elior <Ariel.Elior@qlogic.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/ethernet/broadcom/bnx2x')
-rw-r--r--drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c2
-rw-r--r--drivers/net/ethernet/broadcom/bnx2x/bnx2x_sp.c2
-rw-r--r--drivers/net/ethernet/broadcom/bnx2x/bnx2x_sp.h2
-rw-r--r--drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c1
-rw-r--r--drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.h2
-rw-r--r--drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.c75
-rw-r--r--drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.h9
7 files changed, 88 insertions, 5 deletions
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c
index 336ef3cf5773..07c636815127 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c
@@ -3163,6 +3163,8 @@ static void bnx2x_pf_q_prep_general(struct bnx2x *bp,
3163 gen_init->mtu = bp->dev->mtu; 3163 gen_init->mtu = bp->dev->mtu;
3164 3164
3165 gen_init->cos = cos; 3165 gen_init->cos = cos;
3166
3167 gen_init->fp_hsi = ETH_FP_HSI_VERSION;
3166} 3168}
3167 3169
3168static void bnx2x_pf_rx_q_prep(struct bnx2x *bp, 3170static void bnx2x_pf_rx_q_prep(struct bnx2x *bp,
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sp.c b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sp.c
index 7bc2924a7e24..07cdf9bbffef 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sp.c
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sp.c
@@ -4336,7 +4336,7 @@ static void bnx2x_q_fill_init_general_data(struct bnx2x *bp,
4336 test_bit(BNX2X_Q_FLG_FCOE, flags) ? 4336 test_bit(BNX2X_Q_FLG_FCOE, flags) ?
4337 LLFC_TRAFFIC_TYPE_FCOE : LLFC_TRAFFIC_TYPE_NW; 4337 LLFC_TRAFFIC_TYPE_FCOE : LLFC_TRAFFIC_TYPE_NW;
4338 4338
4339 gen_data->fp_hsi_ver = ETH_FP_HSI_VERSION; 4339 gen_data->fp_hsi_ver = params->fp_hsi;
4340 4340
4341 DP(BNX2X_MSG_SP, "flags: active %d, cos %d, stats en %d\n", 4341 DP(BNX2X_MSG_SP, "flags: active %d, cos %d, stats en %d\n",
4342 gen_data->activate_flg, gen_data->cos, gen_data->statistics_en_flg); 4342 gen_data->activate_flg, gen_data->cos, gen_data->statistics_en_flg);
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sp.h b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sp.h
index e97275f456c0..86baecb7c60c 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sp.h
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sp.h
@@ -937,6 +937,8 @@ struct bnx2x_general_setup_params {
937 u8 spcl_id; 937 u8 spcl_id;
938 u16 mtu; 938 u16 mtu;
939 u8 cos; 939 u8 cos;
940
941 u8 fp_hsi;
940}; 942};
941 943
942struct bnx2x_rxq_setup_params { 944struct bnx2x_rxq_setup_params {
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c
index c88b20af87df..e5aca2de1871 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c
@@ -193,6 +193,7 @@ void bnx2x_vfop_qctor_prep(struct bnx2x *bp,
193 /* Setup-op general parameters */ 193 /* Setup-op general parameters */
194 setup_p->gen_params.spcl_id = vf->sp_cl_id; 194 setup_p->gen_params.spcl_id = vf->sp_cl_id;
195 setup_p->gen_params.stat_id = vfq_stat_id(vf, q); 195 setup_p->gen_params.stat_id = vfq_stat_id(vf, q);
196 setup_p->gen_params.fp_hsi = vf->fp_hsi;
196 197
197 /* Setup-op pause params: 198 /* Setup-op pause params:
198 * Nothing to do, the pause thresholds are set by default to 0 which 199 * Nothing to do, the pause thresholds are set by default to 0 which
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.h b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.h
index 01bafa4ac045..66ee62a0401a 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.h
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.h
@@ -205,6 +205,8 @@ struct bnx2x_virtf {
205 /* slow-path operations */ 205 /* slow-path operations */
206 struct mutex op_mutex; /* one vfop at a time mutex */ 206 struct mutex op_mutex; /* one vfop at a time mutex */
207 enum channel_tlvs op_current; 207 enum channel_tlvs op_current;
208
209 u8 fp_hsi;
208}; 210};
209 211
210#define BNX2X_NR_VIRTFN(bp) ((bp)->vfdb->sriov.nr_virtfn) 212#define BNX2X_NR_VIRTFN(bp) ((bp)->vfdb->sriov.nr_virtfn)
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.c b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.c
index b1d9c44aa56c..be40eabc5304 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.c
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.c
@@ -224,6 +224,7 @@ int bnx2x_vfpf_acquire(struct bnx2x *bp, u8 tx_count, u8 rx_count)
224 struct vfpf_acquire_tlv *req = &bp->vf2pf_mbox->req.acquire; 224 struct vfpf_acquire_tlv *req = &bp->vf2pf_mbox->req.acquire;
225 struct pfvf_acquire_resp_tlv *resp = &bp->vf2pf_mbox->resp.acquire_resp; 225 struct pfvf_acquire_resp_tlv *resp = &bp->vf2pf_mbox->resp.acquire_resp;
226 struct vfpf_port_phys_id_resp_tlv *phys_port_resp; 226 struct vfpf_port_phys_id_resp_tlv *phys_port_resp;
227 struct vfpf_fp_hsi_resp_tlv *fp_hsi_resp;
227 u32 vf_id; 228 u32 vf_id;
228 bool resources_acquired = false; 229 bool resources_acquired = false;
229 230
@@ -237,6 +238,7 @@ int bnx2x_vfpf_acquire(struct bnx2x *bp, u8 tx_count, u8 rx_count)
237 238
238 req->vfdev_info.vf_id = vf_id; 239 req->vfdev_info.vf_id = vf_id;
239 req->vfdev_info.vf_os = 0; 240 req->vfdev_info.vf_os = 0;
241 req->vfdev_info.fp_hsi_ver = ETH_FP_HSI_VERSION;
240 242
241 req->resc_request.num_rxqs = rx_count; 243 req->resc_request.num_rxqs = rx_count;
242 req->resc_request.num_txqs = tx_count; 244 req->resc_request.num_txqs = tx_count;
@@ -316,9 +318,14 @@ int bnx2x_vfpf_acquire(struct bnx2x *bp, u8 tx_count, u8 rx_count)
316 memset(&bp->vf2pf_mbox->resp, 0, 318 memset(&bp->vf2pf_mbox->resp, 0,
317 sizeof(union pfvf_tlvs)); 319 sizeof(union pfvf_tlvs));
318 } else { 320 } else {
319 /* PF reports error */ 321 /* Determine reason of PF failure of acquire process */
320 BNX2X_ERR("Failed to get the requested amount of resources: %d. Breaking...\n", 322 fp_hsi_resp = bnx2x_search_tlv_list(bp, resp,
321 bp->acquire_resp.hdr.status); 323 CHANNEL_TLV_FP_HSI_SUPPORT);
324 if (fp_hsi_resp && !fp_hsi_resp->is_supported)
325 BNX2X_ERR("Old hypervisor - doesn't support current fastpath HSI version; Need to downgrade VF driver [or upgrade hypervisor]\n");
326 else
327 BNX2X_ERR("Failed to get the requested amount of resources: %d. Breaking...\n",
328 bp->acquire_resp.hdr.status);
322 rc = -EAGAIN; 329 rc = -EAGAIN;
323 goto out; 330 goto out;
324 } 331 }
@@ -333,6 +340,25 @@ int bnx2x_vfpf_acquire(struct bnx2x *bp, u8 tx_count, u8 rx_count)
333 bp->flags |= HAS_PHYS_PORT_ID; 340 bp->flags |= HAS_PHYS_PORT_ID;
334 } 341 }
335 342
343 /* Old Hypevisors might not even support the FP_HSI_SUPPORT TLV.
344 * If that's the case, we need to make certain required FW was
345 * supported by such a hypervisor [i.e., v0-v2].
346 */
347 fp_hsi_resp = bnx2x_search_tlv_list(bp, resp,
348 CHANNEL_TLV_FP_HSI_SUPPORT);
349 if (!fp_hsi_resp && (ETH_FP_HSI_VERSION > ETH_FP_HSI_VER_2)) {
350 BNX2X_ERR("Old hypervisor - need to downgrade VF's driver\n");
351
352 /* Since acquire succeeded on the PF side, we need to send a
353 * release message in order to allow future probes.
354 */
355 bnx2x_vfpf_finalize(bp, &req->first_tlv);
356 bnx2x_vfpf_release(bp);
357
358 rc = -EINVAL;
359 goto out;
360 }
361
336 /* get HW info */ 362 /* get HW info */
337 bp->common.chip_id |= (bp->acquire_resp.pfdev_info.chip_num & 0xffff); 363 bp->common.chip_id |= (bp->acquire_resp.pfdev_info.chip_num & 0xffff);
338 bp->link_params.chip_id = bp->common.chip_id; 364 bp->link_params.chip_id = bp->common.chip_id;
@@ -1125,6 +1151,26 @@ static void bnx2x_vf_mbx_resp_phys_port(struct bnx2x *bp,
1125 *offset += sizeof(struct vfpf_port_phys_id_resp_tlv); 1151 *offset += sizeof(struct vfpf_port_phys_id_resp_tlv);
1126} 1152}
1127 1153
1154static void bnx2x_vf_mbx_resp_fp_hsi_ver(struct bnx2x *bp,
1155 struct bnx2x_virtf *vf,
1156 void *buffer,
1157 u16 *offset)
1158{
1159 struct vfpf_fp_hsi_resp_tlv *fp_hsi;
1160
1161 bnx2x_add_tlv(bp, buffer, *offset, CHANNEL_TLV_FP_HSI_SUPPORT,
1162 sizeof(struct vfpf_fp_hsi_resp_tlv));
1163
1164 fp_hsi = (struct vfpf_fp_hsi_resp_tlv *)
1165 (((u8 *)buffer) + *offset);
1166 fp_hsi->is_supported = (vf->fp_hsi > ETH_FP_HSI_VERSION) ? 0 : 1;
1167
1168 /* Offset should continue representing the offset to the tail
1169 * of TLV data (outside this function scope)
1170 */
1171 *offset += sizeof(struct vfpf_fp_hsi_resp_tlv);
1172}
1173
1128static void bnx2x_vf_mbx_acquire_resp(struct bnx2x *bp, struct bnx2x_virtf *vf, 1174static void bnx2x_vf_mbx_acquire_resp(struct bnx2x *bp, struct bnx2x_virtf *vf,
1129 struct bnx2x_vf_mbx *mbx, int vfop_status) 1175 struct bnx2x_vf_mbx *mbx, int vfop_status)
1130{ 1176{
@@ -1219,6 +1265,12 @@ static void bnx2x_vf_mbx_acquire_resp(struct bnx2x *bp, struct bnx2x_virtf *vf,
1219 CHANNEL_TLV_PHYS_PORT_ID)) 1265 CHANNEL_TLV_PHYS_PORT_ID))
1220 bnx2x_vf_mbx_resp_phys_port(bp, vf, &mbx->msg->resp, &length); 1266 bnx2x_vf_mbx_resp_phys_port(bp, vf, &mbx->msg->resp, &length);
1221 1267
1268 /* `New' vfs will want to know if fastpath HSI is supported, since
1269 * if that's not the case they could print into system log the fact
1270 * the driver version must be updated.
1271 */
1272 bnx2x_vf_mbx_resp_fp_hsi_ver(bp, vf, &mbx->msg->resp, &length);
1273
1222 bnx2x_add_tlv(bp, &mbx->msg->resp, length, CHANNEL_TLV_LIST_END, 1274 bnx2x_add_tlv(bp, &mbx->msg->resp, length, CHANNEL_TLV_LIST_END,
1223 sizeof(struct channel_list_end_tlv)); 1275 sizeof(struct channel_list_end_tlv));
1224 1276
@@ -1288,6 +1340,23 @@ static void bnx2x_vf_mbx_acquire(struct bnx2x *bp, struct bnx2x_virtf *vf,
1288 goto out; 1340 goto out;
1289 } 1341 }
1290 1342
1343 /* Verify the VF fastpath HSI can be supported by the loaded FW.
1344 * Linux vfs should be oblivious to changes between v0 and v2.
1345 */
1346 if (bnx2x_vf_mbx_is_windows_vm(bp, &mbx->msg->req.acquire))
1347 vf->fp_hsi = acquire->vfdev_info.fp_hsi_ver;
1348 else
1349 vf->fp_hsi = max_t(u8, acquire->vfdev_info.fp_hsi_ver,
1350 ETH_FP_HSI_VER_2);
1351 if (vf->fp_hsi > ETH_FP_HSI_VERSION) {
1352 DP(BNX2X_MSG_IOV,
1353 "VF [%d] - Can't support acquire request since VF requests a FW version which is too new [%02x > %02x]\n",
1354 vf->abs_vfid, acquire->vfdev_info.fp_hsi_ver,
1355 ETH_FP_HSI_VERSION);
1356 rc = -EINVAL;
1357 goto out;
1358 }
1359
1291 /* acquire the resources */ 1360 /* acquire the resources */
1292 rc = bnx2x_vf_acquire(bp, vf, &acquire->resc_request); 1361 rc = bnx2x_vf_acquire(bp, vf, &acquire->resc_request);
1293 1362
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.h b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.h
index 15670c499a20..b86479fc0d2f 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.h
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.h
@@ -124,7 +124,7 @@ struct vfpf_acquire_tlv {
124#define VF_OS_UNDEFINED (0 << VF_OS_SHIFT) 124#define VF_OS_UNDEFINED (0 << VF_OS_SHIFT)
125#define VF_OS_WINDOWS (1 << VF_OS_SHIFT) 125#define VF_OS_WINDOWS (1 << VF_OS_SHIFT)
126 126
127 u8 padding; 127 u8 fp_hsi_ver;
128 u8 caps; 128 u8 caps;
129#define VF_CAP_SUPPORT_EXT_BULLETIN (1 << 0) 129#define VF_CAP_SUPPORT_EXT_BULLETIN (1 << 0)
130 } vfdev_info; 130 } vfdev_info;
@@ -204,6 +204,12 @@ struct vfpf_port_phys_id_resp_tlv {
204 u8 padding[2]; 204 u8 padding[2];
205}; 205};
206 206
207struct vfpf_fp_hsi_resp_tlv {
208 struct channel_tlv tl;
209 u8 is_supported;
210 u8 padding[3];
211};
212
207#define VFPF_INIT_FLG_STATS_COALESCE (1 << 0) /* when set the VFs queues 213#define VFPF_INIT_FLG_STATS_COALESCE (1 << 0) /* when set the VFs queues
208 * stats will be coalesced on 214 * stats will be coalesced on
209 * the leading RSS queue 215 * the leading RSS queue
@@ -448,6 +454,7 @@ enum channel_tlvs {
448 CHANNEL_TLV_UPDATE_RSS, 454 CHANNEL_TLV_UPDATE_RSS,
449 CHANNEL_TLV_PHYS_PORT_ID, 455 CHANNEL_TLV_PHYS_PORT_ID,
450 CHANNEL_TLV_UPDATE_TPA, 456 CHANNEL_TLV_UPDATE_TPA,
457 CHANNEL_TLV_FP_HSI_SUPPORT,
451 CHANNEL_TLV_MAX 458 CHANNEL_TLV_MAX
452}; 459};
453 460