Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 980df249 authored by Suresh Reddy's avatar Suresh Reddy Committed by David S. Miller
Browse files

be2net: fix port-res desc query of GET_PROFILE_CONFIG FW cmd



Commit 72ef3a88 ("be2net: set pci_func_num while issuing
GET_PROFILE_CONFIG cmd") passed a specific pf_num while issuing a
GET_PROFILE_CONFIG cmd as FW returns descriptors for all functions when
pf_num is zero. But, when pf_num is set to a non-zero value, FW does not
return the Port resource descriptor.
This patch fixes this by setting pf_num to 0 while issuing the query cmd
and adds code to pick the correct NIC resource descriptor from the list of
descriptors returned by FW.

Fixes: 72ef3a88 ("be2net: set pci_func_num while issuing
		     GET_PROFILE_CONFIG cmd")
Signed-off-by: default avatarSuresh Reddy <suresh.reddy@avagotech.com>

Signed-off-by: default avatarSathya Perla <sathya.perla@avagotech.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 04e888de
Loading
Loading
Loading
Loading
+2 −2
Original line number Original line Diff line number Diff line
@@ -570,6 +570,8 @@ struct be_adapter {
	struct be_resources pool_res;	/* resources available for the port */
	struct be_resources pool_res;	/* resources available for the port */
	struct be_resources res;	/* resources available for the func */
	struct be_resources res;	/* resources available for the func */
	u16 num_vfs;			/* Number of VFs provisioned by PF */
	u16 num_vfs;			/* Number of VFs provisioned by PF */
	u8 pf_num;			/* Numbering used by FW, starts at 0 */
	u8 vf_num;			/* Numbering used by FW, starts at 1 */
	u8 virtfn;
	u8 virtfn;
	struct be_vf_cfg *vf_cfg;
	struct be_vf_cfg *vf_cfg;
	bool be3_native;
	bool be3_native;
@@ -587,8 +589,6 @@ struct be_adapter {
	u32 msg_enable;
	u32 msg_enable;
	int be_get_temp_freq;
	int be_get_temp_freq;
	struct be_hwmon hwmon_info;
	struct be_hwmon hwmon_info;
	u8 pf_number;
	u8 pci_func_num;
	struct rss_info rss_info;
	struct rss_info rss_info;
	/* Filters for packets that need to be sent to BMC */
	/* Filters for packets that need to be sent to BMC */
	u32 bmc_filt_mask;
	u32 bmc_filt_mask;
+46 −39
Original line number Original line Diff line number Diff line
@@ -3466,7 +3466,6 @@ int be_cmd_get_cntl_attributes(struct be_adapter *adapter)
	if (!status) {
	if (!status) {
		attribs = attribs_cmd.va + sizeof(struct be_cmd_resp_hdr);
		attribs = attribs_cmd.va + sizeof(struct be_cmd_resp_hdr);
		adapter->hba_port_num = attribs->hba_attribs.phy_port;
		adapter->hba_port_num = attribs->hba_attribs.phy_port;
		adapter->pci_func_num = attribs->pci_func_num;
		serial_num = attribs->hba_attribs.controller_serial_number;
		serial_num = attribs->hba_attribs.controller_serial_number;
		for (i = 0; i < CNTL_SERIAL_NUM_WORDS; i++)
		for (i = 0; i < CNTL_SERIAL_NUM_WORDS; i++)
			adapter->serial_num[i] = le32_to_cpu(serial_num[i]) &
			adapter->serial_num[i] = le32_to_cpu(serial_num[i]) &
@@ -4149,14 +4148,16 @@ int be_cmd_query_port_name(struct be_adapter *adapter)
	return status;
	return status;
}
}


/* Descriptor type */
/* When more than 1 NIC descriptor is present in the descriptor list,
enum {
 * the caller must specify the pf_num to obtain the NIC descriptor
	FUNC_DESC = 1,
 * corresponding to its pci function.
	VFT_DESC = 2
 * get_vft must be true when the caller wants the VF-template desc of the
};
 * PF-pool.

 * The pf_num should be set to PF_NUM_IGNORE when the caller knows
 * that only it's NIC descriptor is present in the descriptor list.
 */
static struct be_nic_res_desc *be_get_nic_desc(u8 *buf, u32 desc_count,
static struct be_nic_res_desc *be_get_nic_desc(u8 *buf, u32 desc_count,
					       int desc_type)
					       bool get_vft, u8 pf_num)
{
{
	struct be_res_desc_hdr *hdr = (struct be_res_desc_hdr *)buf;
	struct be_res_desc_hdr *hdr = (struct be_res_desc_hdr *)buf;
	struct be_nic_res_desc *nic;
	struct be_nic_res_desc *nic;
@@ -4166,40 +4167,42 @@ static struct be_nic_res_desc *be_get_nic_desc(u8 *buf, u32 desc_count,
		if (hdr->desc_type == NIC_RESOURCE_DESC_TYPE_V0 ||
		if (hdr->desc_type == NIC_RESOURCE_DESC_TYPE_V0 ||
		    hdr->desc_type == NIC_RESOURCE_DESC_TYPE_V1) {
		    hdr->desc_type == NIC_RESOURCE_DESC_TYPE_V1) {
			nic = (struct be_nic_res_desc *)hdr;
			nic = (struct be_nic_res_desc *)hdr;
			if (desc_type == FUNC_DESC ||

			    (desc_type == VFT_DESC &&
			if ((pf_num == PF_NUM_IGNORE ||
			     nic->flags & (1 << VFT_SHIFT)))
			     nic->pf_num == pf_num) &&
			    (!get_vft || nic->flags & BIT(VFT_SHIFT)))
				return nic;
				return nic;
		}
		}

		hdr->desc_len = hdr->desc_len ? : RESOURCE_DESC_SIZE_V0;
		hdr->desc_len = hdr->desc_len ? : RESOURCE_DESC_SIZE_V0;
		hdr = (void *)hdr + hdr->desc_len;
		hdr = (void *)hdr + hdr->desc_len;
	}
	}
	return NULL;
	return NULL;
}
}


static struct be_nic_res_desc *be_get_vft_desc(u8 *buf, u32 desc_count)
static struct be_nic_res_desc *be_get_vft_desc(u8 *buf, u32 desc_count,
					       u8 pf_num)
{
{
	return be_get_nic_desc(buf, desc_count, VFT_DESC);
	return be_get_nic_desc(buf, desc_count, true, pf_num);
}
}


static struct be_nic_res_desc *be_get_func_nic_desc(u8 *buf, u32 desc_count)
static struct be_nic_res_desc *be_get_func_nic_desc(u8 *buf, u32 desc_count,
						    u8 pf_num)
{
{
	return be_get_nic_desc(buf, desc_count, FUNC_DESC);
	return be_get_nic_desc(buf, desc_count, false, pf_num);
}
}


static struct be_pcie_res_desc *be_get_pcie_desc(u8 devfn, u8 *buf,
static struct be_pcie_res_desc *be_get_pcie_desc(u8 *buf, u32 desc_count,
						 u32 desc_count)
						 u8 pf_num)
{
{
	struct be_res_desc_hdr *hdr = (struct be_res_desc_hdr *)buf;
	struct be_res_desc_hdr *hdr = (struct be_res_desc_hdr *)buf;
	struct be_pcie_res_desc *pcie;
	struct be_pcie_res_desc *pcie;
	int i;
	int i;


	for (i = 0; i < desc_count; i++) {
	for (i = 0; i < desc_count; i++) {
		if ((hdr->desc_type == PCIE_RESOURCE_DESC_TYPE_V0 ||
		if (hdr->desc_type == PCIE_RESOURCE_DESC_TYPE_V0 ||
		     hdr->desc_type == PCIE_RESOURCE_DESC_TYPE_V1)) {
		    hdr->desc_type == PCIE_RESOURCE_DESC_TYPE_V1) {
			pcie = (struct be_pcie_res_desc *)hdr;
			pcie = (struct be_pcie_res_desc *)hdr;
			if (pcie->pf_num == devfn)
			if (pcie->pf_num == pf_num)
				return pcie;
				return pcie;
		}
		}


@@ -4284,12 +4287,22 @@ int be_cmd_get_func_config(struct be_adapter *adapter, struct be_resources *res)
		u32 desc_count = le32_to_cpu(resp->desc_count);
		u32 desc_count = le32_to_cpu(resp->desc_count);
		struct be_nic_res_desc *desc;
		struct be_nic_res_desc *desc;


		desc = be_get_func_nic_desc(resp->func_param, desc_count);
		/* GET_FUNC_CONFIG returns resource descriptors of the
		 * current function only. So, pf_num should be set to
		 * PF_NUM_IGNORE.
		 */
		desc = be_get_func_nic_desc(resp->func_param, desc_count,
					    PF_NUM_IGNORE);
		if (!desc) {
		if (!desc) {
			status = -EINVAL;
			status = -EINVAL;
			goto err;
			goto err;
		}
		}
		adapter->pf_number = desc->pf_num;

		/* Store pf_num & vf_num for later use in GET_PROFILE_CONFIG */
		adapter->pf_num = desc->pf_num;
		adapter->vf_num = desc->vf_num;

		if (res)
			be_copy_nic_desc(res, desc);
			be_copy_nic_desc(res, desc);
	}
	}
err:
err:
@@ -4300,10 +4313,7 @@ int be_cmd_get_func_config(struct be_adapter *adapter, struct be_resources *res)
	return status;
	return status;
}
}


/* Will use MBOX only if MCCQ has not been created
/* Will use MBOX only if MCCQ has not been created */
 * non-zero domain => a PF is querying this on behalf of a VF
 * zero domain => a PF or a VF is querying this for itself
 */
int be_cmd_get_profile_config(struct be_adapter *adapter,
int be_cmd_get_profile_config(struct be_adapter *adapter,
			      struct be_resources *res, u8 query, u8 domain)
			      struct be_resources *res, u8 query, u8 domain)
{
{
@@ -4333,12 +4343,7 @@ int be_cmd_get_profile_config(struct be_adapter *adapter,
	if (!lancer_chip(adapter))
	if (!lancer_chip(adapter))
		req->hdr.version = 1;
		req->hdr.version = 1;
	req->type = ACTIVE_PROFILE_TYPE;
	req->type = ACTIVE_PROFILE_TYPE;
	/* When a function is querying profile information relating to
	 * itself hdr.pf_number must be set to it's pci_func_num + 1
	 */
	req->hdr.domain = domain;
	req->hdr.domain = domain;
	if (domain == 0)
		req->hdr.pf_num = adapter->pci_func_num + 1;


	/* When QUERY_MODIFIABLE_FIELDS_TYPE bit is set, cmd returns the
	/* When QUERY_MODIFIABLE_FIELDS_TYPE bit is set, cmd returns the
	 * descriptors with all bits set to "1" for the fields which can be
	 * descriptors with all bits set to "1" for the fields which can be
@@ -4354,8 +4359,8 @@ int be_cmd_get_profile_config(struct be_adapter *adapter,
	resp = cmd.va;
	resp = cmd.va;
	desc_count = le16_to_cpu(resp->desc_count);
	desc_count = le16_to_cpu(resp->desc_count);


	pcie = be_get_pcie_desc(adapter->pdev->devfn, resp->func_param,
	pcie = be_get_pcie_desc(resp->func_param, desc_count,
				desc_count);
				adapter->pf_num);
	if (pcie)
	if (pcie)
		res->max_vfs = le16_to_cpu(pcie->num_vfs);
		res->max_vfs = le16_to_cpu(pcie->num_vfs);


@@ -4363,11 +4368,13 @@ int be_cmd_get_profile_config(struct be_adapter *adapter,
	if (port)
	if (port)
		adapter->mc_type = port->mc_type;
		adapter->mc_type = port->mc_type;


	nic = be_get_func_nic_desc(resp->func_param, desc_count);
	nic = be_get_func_nic_desc(resp->func_param, desc_count,
				   adapter->pf_num);
	if (nic)
	if (nic)
		be_copy_nic_desc(res, nic);
		be_copy_nic_desc(res, nic);


	vf_res = be_get_vft_desc(resp->func_param, desc_count);
	vf_res = be_get_vft_desc(resp->func_param, desc_count,
				 adapter->pf_num);
	if (vf_res)
	if (vf_res)
		res->vf_if_cap_flags = vf_res->cap_flags;
		res->vf_if_cap_flags = vf_res->cap_flags;
err:
err:
@@ -4457,7 +4464,7 @@ int be_cmd_config_qos(struct be_adapter *adapter, u32 max_rate, u16 link_speed,
		return be_cmd_set_qos(adapter, max_rate / 10, domain);
		return be_cmd_set_qos(adapter, max_rate / 10, domain);


	be_reset_nic_desc(&nic_desc);
	be_reset_nic_desc(&nic_desc);
	nic_desc.pf_num = adapter->pf_number;
	nic_desc.pf_num = adapter->pf_num;
	nic_desc.vf_num = domain;
	nic_desc.vf_num = domain;
	nic_desc.bw_min = 0;
	nic_desc.bw_min = 0;
	if (lancer_chip(adapter)) {
	if (lancer_chip(adapter)) {
+3 −8
Original line number Original line Diff line number Diff line
@@ -291,9 +291,7 @@ struct be_cmd_req_hdr {
	u32 timeout;		/* dword 1 */
	u32 timeout;		/* dword 1 */
	u32 request_length;	/* dword 2 */
	u32 request_length;	/* dword 2 */
	u8 version;		/* dword 3 */
	u8 version;		/* dword 3 */
	u8 rsvd1;		/* dword 3 */
	u8 rsvd[3];		/* dword 3 */
	u8 pf_num;		/* dword 3 */
	u8 rsvd2;		/* dword 3 */
};
};


#define RESP_HDR_INFO_OPCODE_SHIFT	0	/* bits 0 - 7 */
#define RESP_HDR_INFO_OPCODE_SHIFT	0	/* bits 0 - 7 */
@@ -1676,11 +1674,7 @@ struct mgmt_hba_attribs {


struct mgmt_controller_attrib {
struct mgmt_controller_attrib {
	struct mgmt_hba_attribs hba_attribs;
	struct mgmt_hba_attribs hba_attribs;
	u32 rsvd0[2];
	u32 rsvd0[10];
	u16 rsvd1;
	u8 pci_func_num;
	u8 rsvd2;
	u32 rsvd3[7];
} __packed;
} __packed;


struct be_cmd_req_cntl_attribs {
struct be_cmd_req_cntl_attribs {
@@ -2105,6 +2099,7 @@ struct be_port_res_desc {
#define NV_TYPE_VXLAN				3
#define NV_TYPE_VXLAN				3
#define SOCVID_SHIFT				2	/* Strip outer vlan */
#define SOCVID_SHIFT				2	/* Strip outer vlan */
#define RCVID_SHIFT				4	/* Report vlan */
#define RCVID_SHIFT				4	/* Report vlan */
#define PF_NUM_IGNORE				255
	u8 nv_flags;
	u8 nv_flags;
	u8 rsvd2;
	u8 rsvd2;
	__le16 nv_port;					/* vxlan/gre port */
	__le16 nv_port;					/* vxlan/gre port */
+12 −4
Original line number Original line Diff line number Diff line
@@ -4204,6 +4204,10 @@ static int be_get_config(struct be_adapter *adapter)
	int status, level;
	int status, level;
	u16 profile_id;
	u16 profile_id;


	status = be_cmd_get_cntl_attributes(adapter);
	if (status)
		return status;

	status = be_cmd_query_fw_cfg(adapter);
	status = be_cmd_query_fw_cfg(adapter);
	if (status)
	if (status)
		return status;
		return status;
@@ -4402,10 +4406,14 @@ static int be_setup(struct be_adapter *adapter)
	if (!lancer_chip(adapter))
	if (!lancer_chip(adapter))
		be_cmd_req_native_mode(adapter);
		be_cmd_req_native_mode(adapter);


	/* Need to invoke this cmd first to get the PCI Function Number */
	/* invoke this cmd first to get pf_num and vf_num which are needed
	status = be_cmd_get_cntl_attributes(adapter);
	 * for issuing profile related cmds
	 */
	if (!BEx_chip(adapter)) {
		status = be_cmd_get_func_config(adapter, NULL);
		if (status)
		if (status)
			return status;
			return status;
	}


	if (!BE2_chip(adapter) && be_physfn(adapter))
	if (!BE2_chip(adapter) && be_physfn(adapter))
		be_alloc_sriov_res(adapter);
		be_alloc_sriov_res(adapter);