forked from Minki/linux
be2net: refactor multi-channel config code for Skyhawk-R chip
Currently multi-channel configuration is read via the QUERY_FW_CONFIG cmd. This method has been deprecated by the Skyhawk-R FW. Instead, GET_PROFILE_CONFIG::port-desc must be used to query this configuration. This patch also: a) introduces a few macros to identify certain categories of multi-channel configs 2) re-factors the be_cmd_set_profile_config() code to be able to read any kind of desc (and not just the nic-desc.) Signed-off-by: Vasundhara Volam <vasundhara.volam@emulex.com> Signed-off-by: Sathya Perla <sathya.perla@emulex.com> Signed-off-by: Somnath Kotur <somnath.kotur@emulex.com> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
40263820b4
commit
f93f160b5a
@ -88,7 +88,6 @@ static inline char *nic_name(struct pci_dev *pdev)
|
||||
#define BE_MIN_MTU 256
|
||||
|
||||
#define BE_NUM_VLANS_SUPPORTED 64
|
||||
#define BE_UMC_NUM_VLANS_SUPPORTED 15
|
||||
#define BE_MAX_EQD 128u
|
||||
#define BE_MAX_TX_FRAG_COUNT 30
|
||||
|
||||
@ -293,7 +292,7 @@ struct be_rx_compl_info {
|
||||
u8 ip_csum;
|
||||
u8 l4_csum;
|
||||
u8 ipv6;
|
||||
u8 vtm;
|
||||
u8 qnq;
|
||||
u8 pkt_type;
|
||||
u8 ip_frag;
|
||||
};
|
||||
@ -465,6 +464,7 @@ struct be_adapter {
|
||||
|
||||
u32 port_num;
|
||||
bool promiscuous;
|
||||
u8 mc_type;
|
||||
u32 function_mode;
|
||||
u32 function_caps;
|
||||
u32 rx_fc; /* Rx flow control */
|
||||
@ -534,6 +534,14 @@ static inline u16 be_max_qs(struct be_adapter *adapter)
|
||||
return min_t(u16, num, num_online_cpus());
|
||||
}
|
||||
|
||||
/* Is BE in pvid_tagging mode */
|
||||
#define be_pvid_tagging_enabled(adapter) (adapter->pvid)
|
||||
|
||||
/* Is BE in QNQ multi-channel mode */
|
||||
#define be_is_qnq_mode(adapter) (adapter->mc_type == FLEX10 || \
|
||||
adapter->mc_type == vNIC1 || \
|
||||
adapter->mc_type == UFP)
|
||||
|
||||
#define lancer_chip(adapter) (adapter->pdev->device == OC_DEVICE_ID3 || \
|
||||
adapter->pdev->device == OC_DEVICE_ID4)
|
||||
|
||||
|
@ -3296,6 +3296,21 @@ static struct be_pcie_res_desc *be_get_pcie_desc(u8 devfn, u8 *buf,
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static struct be_port_res_desc *be_get_port_desc(u8 *buf, u32 desc_count)
|
||||
{
|
||||
struct be_res_desc_hdr *hdr = (struct be_res_desc_hdr *)buf;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < desc_count; i++) {
|
||||
if (hdr->desc_type == PORT_RESOURCE_DESC_TYPE_V1)
|
||||
return (struct be_port_res_desc *)hdr;
|
||||
|
||||
hdr->desc_len = hdr->desc_len ? : RESOURCE_DESC_SIZE_V0;
|
||||
hdr = (void *)hdr + hdr->desc_len;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void be_copy_nic_desc(struct be_resources *res,
|
||||
struct be_nic_res_desc *desc)
|
||||
{
|
||||
@ -3439,6 +3454,7 @@ int be_cmd_get_profile_config(struct be_adapter *adapter,
|
||||
{
|
||||
struct be_cmd_resp_get_profile_config *resp;
|
||||
struct be_pcie_res_desc *pcie;
|
||||
struct be_port_res_desc *port;
|
||||
struct be_nic_res_desc *nic;
|
||||
struct be_queue_info *mccq = &adapter->mcc_obj.q;
|
||||
struct be_dma_mem cmd;
|
||||
@ -3466,6 +3482,10 @@ int be_cmd_get_profile_config(struct be_adapter *adapter,
|
||||
if (pcie)
|
||||
res->max_vfs = le16_to_cpu(pcie->num_vfs);
|
||||
|
||||
port = be_get_port_desc(resp->func_param, desc_count);
|
||||
if (port)
|
||||
adapter->mc_type = port->mc_type;
|
||||
|
||||
nic = be_get_nic_desc(resp->func_param, desc_count);
|
||||
if (nic)
|
||||
be_copy_nic_desc(res, nic);
|
||||
|
@ -1098,14 +1098,6 @@ struct be_cmd_resp_query_fw_cfg {
|
||||
u32 function_caps;
|
||||
};
|
||||
|
||||
/* Is BE in a multi-channel mode */
|
||||
static inline bool be_is_mc(struct be_adapter *adapter)
|
||||
{
|
||||
return adapter->function_mode & FLEX10_MODE ||
|
||||
adapter->function_mode & VNIC_MODE ||
|
||||
adapter->function_mode & UMC_ENABLED;
|
||||
}
|
||||
|
||||
/******************** RSS Config ****************************************/
|
||||
/* RSS type Input parameters used to compute RX hash
|
||||
* RSS_ENABLE_IPV4 SRC IPv4, DST IPv4
|
||||
@ -1828,6 +1820,7 @@ struct be_cmd_req_set_ext_fat_caps {
|
||||
#define NIC_RESOURCE_DESC_TYPE_V0 0x41
|
||||
#define PCIE_RESOURCE_DESC_TYPE_V1 0x50
|
||||
#define NIC_RESOURCE_DESC_TYPE_V1 0x51
|
||||
#define PORT_RESOURCE_DESC_TYPE_V1 0x55
|
||||
#define MAX_RESOURCE_DESC 264
|
||||
|
||||
/* QOS unit number */
|
||||
@ -1891,6 +1884,33 @@ struct be_nic_res_desc {
|
||||
u32 rsvd8[7];
|
||||
} __packed;
|
||||
|
||||
/************ Multi-Channel type ***********/
|
||||
enum mc_type {
|
||||
MC_NONE = 0x01,
|
||||
UMC = 0x02,
|
||||
FLEX10 = 0x03,
|
||||
vNIC1 = 0x04,
|
||||
nPAR = 0x05,
|
||||
UFP = 0x06,
|
||||
vNIC2 = 0x07
|
||||
};
|
||||
|
||||
struct be_port_res_desc {
|
||||
struct be_res_desc_hdr hdr;
|
||||
u8 rsvd0;
|
||||
u8 flags;
|
||||
u8 rsvd1;
|
||||
u8 mc_type;
|
||||
u16 rsvd2;
|
||||
u32 rsvd3[20];
|
||||
} __packed;
|
||||
|
||||
/* Is BE in a multi-channel mode */
|
||||
static inline bool be_is_mc(struct be_adapter *adapter)
|
||||
{
|
||||
return adapter->mc_type > MC_NONE;
|
||||
}
|
||||
|
||||
struct be_cmd_req_get_func_config {
|
||||
struct be_cmd_req_hdr hdr;
|
||||
};
|
||||
|
@ -368,7 +368,7 @@ struct amap_eth_rx_compl_v0 {
|
||||
u8 numfrags[3]; /* dword 1 */
|
||||
u8 rss_flush; /* dword 2 */
|
||||
u8 cast_enc[2]; /* dword 2 */
|
||||
u8 vtm; /* dword 2 */
|
||||
u8 qnq; /* dword 2 */
|
||||
u8 rss_bank; /* dword 2 */
|
||||
u8 rsvd1[23]; /* dword 2 */
|
||||
u8 lro_pkt; /* dword 2 */
|
||||
@ -401,7 +401,7 @@ struct amap_eth_rx_compl_v1 {
|
||||
u8 numfrags[3]; /* dword 1 */
|
||||
u8 rss_flush; /* dword 2 */
|
||||
u8 cast_enc[2]; /* dword 2 */
|
||||
u8 vtm; /* dword 2 */
|
||||
u8 qnq; /* dword 2 */
|
||||
u8 rss_bank; /* dword 2 */
|
||||
u8 port[2]; /* dword 2 */
|
||||
u8 vntagp; /* dword 2 */
|
||||
|
@ -945,9 +945,9 @@ static struct sk_buff *be_xmit_workarounds(struct be_adapter *adapter,
|
||||
}
|
||||
|
||||
/* If vlan tag is already inlined in the packet, skip HW VLAN
|
||||
* tagging in UMC mode
|
||||
* tagging in pvid-tagging mode
|
||||
*/
|
||||
if ((adapter->function_mode & UMC_ENABLED) &&
|
||||
if (be_pvid_tagging_enabled(adapter) &&
|
||||
veh->h_vlan_proto == htons(ETH_P_8021Q))
|
||||
*skip_hw_vlan = true;
|
||||
|
||||
@ -1660,7 +1660,7 @@ static void be_parse_rx_compl_v1(struct be_eth_rx_compl *compl,
|
||||
rxcp->rss_hash =
|
||||
AMAP_GET_BITS(struct amap_eth_rx_compl_v1, rsshash, compl);
|
||||
if (rxcp->vlanf) {
|
||||
rxcp->vtm = AMAP_GET_BITS(struct amap_eth_rx_compl_v1, vtm,
|
||||
rxcp->qnq = AMAP_GET_BITS(struct amap_eth_rx_compl_v1, qnq,
|
||||
compl);
|
||||
rxcp->vlan_tag = AMAP_GET_BITS(struct amap_eth_rx_compl_v1, vlan_tag,
|
||||
compl);
|
||||
@ -1690,7 +1690,7 @@ static void be_parse_rx_compl_v0(struct be_eth_rx_compl *compl,
|
||||
rxcp->rss_hash =
|
||||
AMAP_GET_BITS(struct amap_eth_rx_compl_v0, rsshash, compl);
|
||||
if (rxcp->vlanf) {
|
||||
rxcp->vtm = AMAP_GET_BITS(struct amap_eth_rx_compl_v0, vtm,
|
||||
rxcp->qnq = AMAP_GET_BITS(struct amap_eth_rx_compl_v0, qnq,
|
||||
compl);
|
||||
rxcp->vlan_tag = AMAP_GET_BITS(struct amap_eth_rx_compl_v0, vlan_tag,
|
||||
compl);
|
||||
@ -1723,9 +1723,11 @@ static struct be_rx_compl_info *be_rx_compl_get(struct be_rx_obj *rxo)
|
||||
rxcp->l4_csum = 0;
|
||||
|
||||
if (rxcp->vlanf) {
|
||||
/* vlanf could be wrongly set in some cards.
|
||||
* ignore if vtm is not set */
|
||||
if ((adapter->function_mode & FLEX10_MODE) && !rxcp->vtm)
|
||||
/* In QNQ modes, if qnq bit is not set, then the packet was
|
||||
* tagged only with the transparent outer vlan-tag and must
|
||||
* not be treated as a vlan packet by host
|
||||
*/
|
||||
if (be_is_qnq_mode(adapter) && !rxcp->qnq)
|
||||
rxcp->vlanf = 0;
|
||||
|
||||
if (!lancer_chip(adapter))
|
||||
@ -3109,6 +3111,22 @@ err:
|
||||
return status;
|
||||
}
|
||||
|
||||
/* Converting function_mode bits on BE3 to SH mc_type enums */
|
||||
|
||||
static u8 be_convert_mc_type(u32 function_mode)
|
||||
{
|
||||
if (function_mode & VNIC_MODE && function_mode & FLEX10_MODE)
|
||||
return vNIC1;
|
||||
else if (function_mode & FLEX10_MODE)
|
||||
return FLEX10;
|
||||
else if (function_mode & VNIC_MODE)
|
||||
return vNIC2;
|
||||
else if (function_mode & UMC_ENABLED)
|
||||
return UMC;
|
||||
else
|
||||
return MC_NONE;
|
||||
}
|
||||
|
||||
/* On BE2/BE3 FW does not suggest the supported limits */
|
||||
static void BEx_get_resources(struct be_adapter *adapter,
|
||||
struct be_resources *res)
|
||||
@ -3129,12 +3147,23 @@ static void BEx_get_resources(struct be_adapter *adapter,
|
||||
else
|
||||
res->max_uc_mac = BE_VF_UC_PMAC_COUNT;
|
||||
|
||||
if (adapter->function_mode & FLEX10_MODE)
|
||||
res->max_vlans = BE_NUM_VLANS_SUPPORTED/8;
|
||||
else if (adapter->function_mode & UMC_ENABLED)
|
||||
res->max_vlans = BE_UMC_NUM_VLANS_SUPPORTED;
|
||||
else
|
||||
adapter->mc_type = be_convert_mc_type(adapter->function_mode);
|
||||
|
||||
if (be_is_mc(adapter)) {
|
||||
/* Assuming that there are 4 channels per port,
|
||||
* when multi-channel is enabled
|
||||
*/
|
||||
if (be_is_qnq_mode(adapter))
|
||||
res->max_vlans = BE_NUM_VLANS_SUPPORTED/8;
|
||||
else
|
||||
/* In a non-qnq multichannel mode, the pvid
|
||||
* takes up one vlan entry
|
||||
*/
|
||||
res->max_vlans = (BE_NUM_VLANS_SUPPORTED / 4) - 1;
|
||||
} else {
|
||||
res->max_vlans = BE_NUM_VLANS_SUPPORTED;
|
||||
}
|
||||
|
||||
res->max_mcast_mac = BE_MAX_MC;
|
||||
|
||||
/* For BE3 1Gb ports, F/W does not properly support multiple TXQs */
|
||||
@ -4417,14 +4446,32 @@ static bool be_reset_required(struct be_adapter *adapter)
|
||||
|
||||
static char *mc_name(struct be_adapter *adapter)
|
||||
{
|
||||
if (adapter->function_mode & FLEX10_MODE)
|
||||
return "FLEX10";
|
||||
else if (adapter->function_mode & VNIC_MODE)
|
||||
return "vNIC";
|
||||
else if (adapter->function_mode & UMC_ENABLED)
|
||||
return "UMC";
|
||||
else
|
||||
return "";
|
||||
char *str = ""; /* default */
|
||||
|
||||
switch (adapter->mc_type) {
|
||||
case UMC:
|
||||
str = "UMC";
|
||||
break;
|
||||
case FLEX10:
|
||||
str = "FLEX10";
|
||||
break;
|
||||
case vNIC1:
|
||||
str = "vNIC-1";
|
||||
break;
|
||||
case nPAR:
|
||||
str = "nPAR";
|
||||
break;
|
||||
case UFP:
|
||||
str = "UFP";
|
||||
break;
|
||||
case vNIC2:
|
||||
str = "vNIC-2";
|
||||
break;
|
||||
default:
|
||||
str = "";
|
||||
}
|
||||
|
||||
return str;
|
||||
}
|
||||
|
||||
static inline char *func_name(struct be_adapter *adapter)
|
||||
|
Loading…
Reference in New Issue
Block a user