Commit 05cc5a39 authored by Yuval Mintz's avatar Yuval Mintz Committed by David S. Miller

bnx2x: add vlan filtering offload

Current driver always uses vlan-promisc mode, i.e., it receives both
tagged and untagged traffic and lets the network stack drop packets
tagged with unrequested vlan tags.

This patch implements vlan-filtering offload in the driver -
Unless explicitly configured to promisc mode, only untagged packets or
packets tagged with requested vlans would reach the Rx flow.
Signed-off-by: default avatarYuval Mintz <Yuval.Mintz@qlogic.com>
Signed-off-by: default avatarAriel Elior <Ariel.Elior@qlogic.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent e82a08b0
......@@ -1228,6 +1228,10 @@ struct bnx2x_slowpath {
struct eth_classify_rules_ramrod_data e2;
} mac_rdata;
union {
struct eth_classify_rules_ramrod_data e2;
} vlan_rdata;
union {
struct tstorm_eth_mac_filter_config e1x;
struct eth_filter_rules_ramrod_data e2;
......@@ -1410,6 +1414,9 @@ struct bnx2x_sp_objs {
/* Queue State object */
struct bnx2x_queue_sp_obj q_obj;
/* VLANs object */
struct bnx2x_vlan_mac_obj vlan_obj;
};
struct bnx2x_fp_stats {
......@@ -1427,6 +1434,12 @@ enum {
SUB_MF_MODE_BD,
};
struct bnx2x_vlan_entry {
struct list_head link;
u16 vid;
bool hw;
};
struct bnx2x {
/* Fields used in the tx and intr/napi performance paths
* are grouped together in the beginning of the structure
......@@ -1865,8 +1878,6 @@ struct bnx2x {
int dcb_version;
/* CAM credit pools */
/* used only in sriov */
struct bnx2x_credit_pool_obj vlans_pool;
struct bnx2x_credit_pool_obj macs_pool;
......@@ -1929,6 +1940,11 @@ struct bnx2x {
u16 rx_filter;
struct bnx2x_link_report_data vf_link_vars;
struct list_head vlan_reg;
u16 vlan_cnt;
u16 vlan_credit;
u16 vxlan_dst_port;
bool accept_any_vlan;
};
/* Tx queues may be less or equal to Rx queues */
......@@ -1956,23 +1972,14 @@ extern int num_queues;
#define RSS_IPV6_TCP_CAP_MASK \
TSTORM_ETH_FUNCTION_COMMON_CONFIG_RSS_IPV6_TCP_CAPABILITY
/* func init flags */
#define FUNC_FLG_RSS 0x0001
#define FUNC_FLG_STATS 0x0002
/* removed FUNC_FLG_UNMATCHED 0x0004 */
#define FUNC_FLG_TPA 0x0008
#define FUNC_FLG_SPQ 0x0010
#define FUNC_FLG_LEADING 0x0020 /* PF only */
#define FUNC_FLG_LEADING_STATS 0x0040
struct bnx2x_func_init_params {
/* dma */
dma_addr_t fw_stat_map; /* valid iff FUNC_FLG_STATS */
dma_addr_t spq_map; /* valid iff FUNC_FLG_SPQ */
bool spq_active;
dma_addr_t spq_map;
u16 spq_prod;
u16 func_flgs;
u16 func_id; /* abs fid */
u16 pf_id;
u16 spq_prod; /* valid iff FUNC_FLG_SPQ */
};
#define for_each_cnic_queue(bp, var) \
......@@ -2082,6 +2089,11 @@ struct bnx2x_func_init_params {
int bnx2x_set_mac_one(struct bnx2x *bp, u8 *mac,
struct bnx2x_vlan_mac_obj *obj, bool set,
int mac_type, unsigned long *ramrod_flags);
int bnx2x_set_vlan_one(struct bnx2x *bp, u16 vlan,
struct bnx2x_vlan_mac_obj *obj, bool set,
unsigned long *ramrod_flags);
/**
* bnx2x_del_all_macs - delete all MACs configured for the specific MAC object
*
......@@ -2486,6 +2498,7 @@ void bnx2x_igu_clear_sb_gen(struct bnx2x *bp, u8 func, u8 idu_sb_id,
#define VF_ACQUIRE_THRESH 3
#define VF_ACQUIRE_MAC_FILTERS 1
#define VF_ACQUIRE_MC_FILTERS 10
#define VF_ACQUIRE_VLAN_FILTERS 2 /* VLAN0 + 'real' VLAN */
#define GOOD_ME_REG(me_reg) (((me_reg) & ME_REG_VF_VALID) && \
(!((me_reg) & ME_REG_VF_ERR)))
......@@ -2596,4 +2609,9 @@ void bnx2x_set_rx_ts(struct bnx2x *bp, struct sk_buff *skb);
#define BNX2X_MAX_PHC_DRIFT 31000000
#define BNX2X_PTP_TX_TIMEOUT
/* Re-configure all previously configured vlan filters.
* Meant for implicit re-load flows.
*/
int bnx2x_vlan_reconfigure_vid(struct bnx2x *bp);
#endif /* bnx2x.h */
......@@ -2848,6 +2848,11 @@ int bnx2x_nic_load(struct bnx2x *bp, int load_mode)
/* Start fast path */
/* Re-configure vlan filters */
rc = bnx2x_vlan_reconfigure_vid(bp);
if (rc)
LOAD_ERROR_EXIT(bp, load_error3);
/* Initialize Rx filter. */
bnx2x_set_rx_mode_inner(bp);
......
......@@ -1066,6 +1066,15 @@ static inline void bnx2x_init_vlan_mac_fp_objs(struct bnx2x_fastpath *fp,
BNX2X_FILTER_MAC_PENDING,
&bp->sp_state, obj_type,
&bp->macs_pool);
if (!CHIP_IS_E1x(bp))
bnx2x_init_vlan_obj(bp, &bnx2x_sp_obj(bp, fp).vlan_obj,
fp->cl_id, fp->cid, BP_FUNC(bp),
bnx2x_sp(bp, vlan_rdata),
bnx2x_sp_mapping(bp, vlan_rdata),
BNX2X_FILTER_VLAN_PENDING,
&bp->sp_state, obj_type,
&bp->vlans_pool);
}
/**
......@@ -1125,7 +1134,7 @@ static inline void bnx2x_init_bp_objs(struct bnx2x *bp)
bnx2x_init_mac_credit_pool(bp, &bp->macs_pool, BP_FUNC(bp),
bnx2x_get_path_func_num(bp));
bnx2x_init_vlan_credit_pool(bp, &bp->vlans_pool, BP_ABS_FUNC(bp)>>1,
bnx2x_init_vlan_credit_pool(bp, &bp->vlans_pool, BP_FUNC(bp),
bnx2x_get_path_func_num(bp));
/* RSS configuration object */
......@@ -1135,6 +1144,8 @@ static inline void bnx2x_init_bp_objs(struct bnx2x *bp)
bnx2x_sp_mapping(bp, rss_rdata),
BNX2X_FILTER_RSS_CONF_PENDING, &bp->sp_state,
BNX2X_OBJ_TYPE_RX);
bp->vlan_credit = PF_VLAN_CREDIT_E2(bp, bnx2x_get_path_func_num(bp));
}
static inline u8 bnx2x_fp_qzone_id(struct bnx2x_fastpath *fp)
......
......@@ -3067,7 +3067,7 @@ void bnx2x_func_init(struct bnx2x *bp, struct bnx2x_func_init_params *p)
storm_memset_func_en(bp, p->func_id, 1);
/* spq */
if (p->func_flgs & FUNC_FLG_SPQ) {
if (p->spq_active) {
storm_memset_spq_addr(bp, p->spq_map, p->func_id);
REG_WR(bp, XSEM_REG_FAST_MEMORY +
XSTORM_SPQ_PROD_OFFSET(p->func_id), p->spq_prod);
......@@ -3283,7 +3283,6 @@ static void bnx2x_pf_init(struct bnx2x *bp)
{
struct bnx2x_func_init_params func_init = {0};
struct event_ring_data eq_data = { {0} };
u16 flags;
if (!CHIP_IS_E1x(bp)) {
/* reset IGU PF statistics: MSIX + ATTN */
......@@ -3300,15 +3299,7 @@ static void bnx2x_pf_init(struct bnx2x *bp)
BP_FUNC(bp) : BP_VN(bp))*4, 0);
}
/* function setup flags */
flags = (FUNC_FLG_STATS | FUNC_FLG_LEADING | FUNC_FLG_SPQ);
/* This flag is relevant for E1x only.
* E2 doesn't have a TPA configuration in a function level.
*/
flags |= (bp->dev->features & NETIF_F_LRO) ? FUNC_FLG_TPA : 0;
func_init.func_flgs = flags;
func_init.spq_active = true;
func_init.pf_id = BP_FUNC(bp);
func_init.func_id = BP_FUNC(bp);
func_init.spq_map = bp->spq_mapping;
......@@ -5303,6 +5294,10 @@ static void bnx2x_handle_classification_eqe(struct bnx2x *bp,
else
vlan_mac_obj = &bp->sp_objs[cid].mac_obj;
break;
case BNX2X_FILTER_VLAN_PENDING:
DP(BNX2X_MSG_SP, "Got SETUP_VLAN completions\n");
vlan_mac_obj = &bp->sp_objs[cid].vlan_obj;
break;
case BNX2X_FILTER_MCAST_PENDING:
DP(BNX2X_MSG_SP, "Got SETUP_MCAST completions\n");
......@@ -5617,7 +5612,7 @@ static void bnx2x_eq_int(struct bnx2x *bp)
BNX2X_STATE_DIAG):
case (EVENT_RING_OPCODE_CLASSIFICATION_RULES |
BNX2X_STATE_CLOSING_WAIT4_HALT):
DP(BNX2X_MSG_SP, "got (un)set mac ramrod\n");
DP(BNX2X_MSG_SP, "got (un)set vlan/mac ramrod\n");
bnx2x_handle_classification_eqe(bp, elem);
break;
......@@ -6205,6 +6200,11 @@ static int bnx2x_fill_accept_flags(struct bnx2x *bp, u32 rx_mode,
__set_bit(BNX2X_ACCEPT_MULTICAST, tx_accept_flags);
__set_bit(BNX2X_ACCEPT_BROADCAST, tx_accept_flags);
if (bp->accept_any_vlan) {
__set_bit(BNX2X_ACCEPT_ANY_VLAN, rx_accept_flags);
__set_bit(BNX2X_ACCEPT_ANY_VLAN, tx_accept_flags);
}
break;
case BNX2X_RX_MODE_ALLMULTI:
__set_bit(BNX2X_ACCEPT_UNICAST, rx_accept_flags);
......@@ -6216,6 +6216,11 @@ static int bnx2x_fill_accept_flags(struct bnx2x *bp, u32 rx_mode,
__set_bit(BNX2X_ACCEPT_ALL_MULTICAST, tx_accept_flags);
__set_bit(BNX2X_ACCEPT_BROADCAST, tx_accept_flags);
if (bp->accept_any_vlan) {
__set_bit(BNX2X_ACCEPT_ANY_VLAN, rx_accept_flags);
__set_bit(BNX2X_ACCEPT_ANY_VLAN, tx_accept_flags);
}
break;
case BNX2X_RX_MODE_PROMISC:
/* According to definition of SI mode, iface in promisc mode
......@@ -6236,18 +6241,15 @@ static int bnx2x_fill_accept_flags(struct bnx2x *bp, u32 rx_mode,
else
__set_bit(BNX2X_ACCEPT_UNICAST, tx_accept_flags);
__set_bit(BNX2X_ACCEPT_ANY_VLAN, rx_accept_flags);
__set_bit(BNX2X_ACCEPT_ANY_VLAN, tx_accept_flags);
break;
default:
BNX2X_ERR("Unknown rx_mode: %d\n", rx_mode);
return -EINVAL;
}
/* Set ACCEPT_ANY_VLAN as we do not enable filtering by VLAN */
if (rx_mode != BNX2X_RX_MODE_NONE) {
__set_bit(BNX2X_ACCEPT_ANY_VLAN, rx_accept_flags);
__set_bit(BNX2X_ACCEPT_ANY_VLAN, tx_accept_flags);
}
return 0;
}
......@@ -8441,6 +8443,42 @@ int bnx2x_set_mac_one(struct bnx2x *bp, u8 *mac,
return rc;
}
int bnx2x_set_vlan_one(struct bnx2x *bp, u16 vlan,
struct bnx2x_vlan_mac_obj *obj, bool set,
unsigned long *ramrod_flags)
{
int rc;
struct bnx2x_vlan_mac_ramrod_params ramrod_param;
memset(&ramrod_param, 0, sizeof(ramrod_param));
/* Fill general parameters */
ramrod_param.vlan_mac_obj = obj;
ramrod_param.ramrod_flags = *ramrod_flags;
/* Fill a user request section if needed */
if (!test_bit(RAMROD_CONT, ramrod_flags)) {
ramrod_param.user_req.u.vlan.vlan = vlan;
/* Set the command: ADD or DEL */
if (set)
ramrod_param.user_req.cmd = BNX2X_VLAN_MAC_ADD;
else
ramrod_param.user_req.cmd = BNX2X_VLAN_MAC_DEL;
}
rc = bnx2x_config_vlan_mac(bp, &ramrod_param);
if (rc == -EEXIST) {
/* Do not treat adding same vlan as error. */
DP(BNX2X_MSG_SP, "Failed to schedule ADD operations: %d\n", rc);
rc = 0;
} else if (rc < 0) {
BNX2X_ERR("%s VLAN failed\n", (set ? "Set" : "Del"));
}
return rc;
}
int bnx2x_del_all_macs(struct bnx2x *bp,
struct bnx2x_vlan_mac_obj *mac_obj,
int mac_type, bool wait_for_comp)
......@@ -12140,6 +12178,7 @@ static int bnx2x_init_bp(struct bnx2x *bp)
mutex_init(&bp->drv_info_mutex);
sema_init(&bp->stats_lock, 1);
bp->drv_info_mng_owner = false;
INIT_LIST_HEAD(&bp->vlan_reg);
INIT_DELAYED_WORK(&bp->sp_task, bnx2x_sp_task);
INIT_DELAYED_WORK(&bp->sp_rtnl_task, bnx2x_sp_rtnl_task);
......@@ -12658,6 +12697,169 @@ static netdev_features_t bnx2x_features_check(struct sk_buff *skb,
return vxlan_features_check(skb, features);
}
static int __bnx2x_vlan_configure_vid(struct bnx2x *bp, u16 vid, bool add)
{
int rc;
if (IS_PF(bp)) {
unsigned long ramrod_flags = 0;
__set_bit(RAMROD_COMP_WAIT, &ramrod_flags);
rc = bnx2x_set_vlan_one(bp, vid, &bp->sp_objs->vlan_obj,
add, &ramrod_flags);
} else {
rc = bnx2x_vfpf_update_vlan(bp, vid, bp->fp->index, add);
}
return rc;
}
int bnx2x_vlan_reconfigure_vid(struct bnx2x *bp)
{
struct bnx2x_vlan_entry *vlan;
int rc = 0;
if (!bp->vlan_cnt) {
DP(NETIF_MSG_IFUP, "No need to re-configure vlan filters\n");
return 0;
}
list_for_each_entry(vlan, &bp->vlan_reg, link) {
/* Prepare for cleanup in case of errors */
if (rc) {
vlan->hw = false;
continue;
}
if (!vlan->hw)
continue;
DP(NETIF_MSG_IFUP, "Re-configuring vlan 0x%04x\n", vlan->vid);
rc = __bnx2x_vlan_configure_vid(bp, vlan->vid, true);
if (rc) {
BNX2X_ERR("Unable to configure VLAN %d\n", vlan->vid);
vlan->hw = false;
rc = -EINVAL;
continue;
}
}
return rc;
}
static int bnx2x_vlan_rx_add_vid(struct net_device *dev, __be16 proto, u16 vid)
{
struct bnx2x *bp = netdev_priv(dev);
struct bnx2x_vlan_entry *vlan;
bool hw = false;
int rc = 0;
if (!netif_running(bp->dev)) {
DP(NETIF_MSG_IFUP,
"Ignoring VLAN configuration the interface is down\n");
return -EFAULT;
}
DP(NETIF_MSG_IFUP, "Adding VLAN %d\n", vid);
vlan = kmalloc(sizeof(*vlan), GFP_KERNEL);
if (!vlan)
return -ENOMEM;
bp->vlan_cnt++;
if (bp->vlan_cnt > bp->vlan_credit && !bp->accept_any_vlan) {
DP(NETIF_MSG_IFUP, "Accept all VLAN raised\n");
bp->accept_any_vlan = true;
if (IS_PF(bp))
bnx2x_set_rx_mode_inner(bp);
else
bnx2x_vfpf_storm_rx_mode(bp);
} else if (bp->vlan_cnt <= bp->vlan_credit) {
rc = __bnx2x_vlan_configure_vid(bp, vid, true);
hw = true;
}
vlan->vid = vid;
vlan->hw = hw;
if (!rc) {
list_add(&vlan->link, &bp->vlan_reg);
} else {
bp->vlan_cnt--;
kfree(vlan);
}
DP(NETIF_MSG_IFUP, "Adding VLAN result %d\n", rc);
return rc;
}
static int bnx2x_vlan_rx_kill_vid(struct net_device *dev, __be16 proto, u16 vid)
{
struct bnx2x *bp = netdev_priv(dev);
struct bnx2x_vlan_entry *vlan;
int rc = 0;
if (!netif_running(bp->dev)) {
DP(NETIF_MSG_IFUP,
"Ignoring VLAN configuration the interface is down\n");
return -EFAULT;
}
DP(NETIF_MSG_IFUP, "Removing VLAN %d\n", vid);
if (!bp->vlan_cnt) {
BNX2X_ERR("Unable to kill VLAN %d\n", vid);
return -EINVAL;
}
list_for_each_entry(vlan, &bp->vlan_reg, link)
if (vlan->vid == vid)
break;
if (vlan->vid != vid) {
BNX2X_ERR("Unable to kill VLAN %d - not found\n", vid);
return -EINVAL;
}
if (vlan->hw)
rc = __bnx2x_vlan_configure_vid(bp, vid, false);
list_del(&vlan->link);
kfree(vlan);
bp->vlan_cnt--;
if (bp->vlan_cnt <= bp->vlan_credit && bp->accept_any_vlan) {
/* Configure all non-configured entries */
list_for_each_entry(vlan, &bp->vlan_reg, link) {
if (vlan->hw)
continue;
rc = __bnx2x_vlan_configure_vid(bp, vlan->vid, true);
if (rc) {
BNX2X_ERR("Unable to config VLAN %d\n",
vlan->vid);
continue;
}
DP(NETIF_MSG_IFUP, "HW configured for VLAN %d\n",
vlan->vid);
vlan->hw = true;
}
DP(NETIF_MSG_IFUP, "Accept all VLAN Removed\n");
bp->accept_any_vlan = false;
if (IS_PF(bp))
bnx2x_set_rx_mode_inner(bp);
else
bnx2x_vfpf_storm_rx_mode(bp);
}
DP(NETIF_MSG_IFUP, "Removing VLAN result %d\n", rc);
return rc;
}
static const struct net_device_ops bnx2x_netdev_ops = {
.ndo_open = bnx2x_open,
.ndo_stop = bnx2x_close,
......@@ -12671,6 +12873,8 @@ static const struct net_device_ops bnx2x_netdev_ops = {
.ndo_fix_features = bnx2x_fix_features,
.ndo_set_features = bnx2x_set_features,
.ndo_tx_timeout = bnx2x_tx_timeout,
.ndo_vlan_rx_add_vid = bnx2x_vlan_rx_add_vid,
.ndo_vlan_rx_kill_vid = bnx2x_vlan_rx_kill_vid,
#ifdef CONFIG_NET_POLL_CONTROLLER
.ndo_poll_controller = poll_bnx2x,
#endif
......@@ -12881,6 +13085,16 @@ static int bnx2x_init_dev(struct bnx2x *bp, struct pci_dev *pdev,
dev->vlan_features = NETIF_F_SG | NETIF_F_IP_CSUM | NETIF_F_IPV6_CSUM |
NETIF_F_TSO | NETIF_F_TSO_ECN | NETIF_F_TSO6 | NETIF_F_HIGHDMA;
/* VF with OLD Hypervisor or old PF do not support filtering */
if (IS_PF(bp)) {
if (CHIP_IS_E1x(bp))
bp->accept_any_vlan = true;
else
dev->hw_features |= NETIF_F_HW_VLAN_CTAG_FILTER;
} else if (bp->acquire_resp.pfdev_info.pf_cap & PFVF_CAP_VLAN_FILTER) {
dev->hw_features |= NETIF_F_HW_VLAN_CTAG_FILTER;
}
dev->features |= dev->hw_features | NETIF_F_HW_VLAN_CTAG_RX;
dev->features |= NETIF_F_HIGHDMA;
......
......@@ -1413,6 +1413,14 @@ void bnx2x_init_vlan_obj(struct bnx2x *bp,
unsigned long *pstate, bnx2x_obj_type type,
struct bnx2x_credit_pool_obj *vlans_pool);
void bnx2x_init_vlan_mac_obj(struct bnx2x *bp,
struct bnx2x_vlan_mac_obj *vlan_mac_obj,
u8 cl_id, u32 cid, u8 func_id, void *rdata,
dma_addr_t rdata_mapping, int state,
unsigned long *pstate, bnx2x_obj_type type,
struct bnx2x_credit_pool_obj *macs_pool,
struct bnx2x_credit_pool_obj *vlans_pool);
int bnx2x_vlan_mac_h_read_lock(struct bnx2x *bp,
struct bnx2x_vlan_mac_obj *o);
void bnx2x_vlan_mac_h_read_unlock(struct bnx2x *bp,
......@@ -1483,6 +1491,8 @@ void bnx2x_init_mac_credit_pool(struct bnx2x *bp,
void bnx2x_init_vlan_credit_pool(struct bnx2x *bp,
struct bnx2x_credit_pool_obj *p, u8 func_id,
u8 func_num);
void bnx2x_init_credit_pool(struct bnx2x_credit_pool_obj *p,
int base, int credit);
/****************** RSS CONFIGURATION ****************/
void bnx2x_init_rss_config_obj(struct bnx2x *bp,
......@@ -1510,4 +1520,12 @@ int bnx2x_config_rss(struct bnx2x *bp,
void bnx2x_get_rss_ind_table(struct bnx2x_rss_config_obj *rss_obj,
u8 *ind_table);
#define PF_MAC_CREDIT_E2(bp, func_num) \
((MAX_MAC_CREDIT_E2 - GET_NUM_VFS_PER_PATH(bp) * VF_MAC_CREDIT_CNT) / \
func_num + GET_NUM_VFS_PER_PF(bp) * VF_MAC_CREDIT_CNT)
#define PF_VLAN_CREDIT_E2(bp, func_num) \
((MAX_MAC_CREDIT_E2 - GET_NUM_VFS_PER_PATH(bp) * VF_VLAN_CREDIT_CNT) / \
func_num + GET_NUM_VFS_PER_PF(bp) * VF_VLAN_CREDIT_CNT)
#endif /* BNX2X_SP_VERBS */
......@@ -77,7 +77,10 @@ struct bnx2x_vf_queue {
/* VLANs object */
struct bnx2x_vlan_mac_obj vlan_obj;
atomic_t vlan_count; /* 0 means vlan-0 is set ~ untagged */
/* VLAN-MACs object */
struct bnx2x_vlan_mac_obj vlan_mac_obj;
unsigned long accept_flags; /* last accept flags configured */
/* Queue Slow-path State object */
......@@ -105,8 +108,10 @@ struct bnx2x_virtf;
struct bnx2x_vf_mac_vlan_filter {
int type;
#define BNX2X_VF_FILTER_MAC 1
#define BNX2X_VF_FILTER_VLAN 2
#define BNX2X_VF_FILTER_MAC BIT(0)
#define BNX2X_VF_FILTER_VLAN BIT(1)
#define BNX2X_VF_FILTER_VLAN_MAC \
(BNX2X_VF_FILTER_MAC | BNX2X_VF_FILTER_VLAN) /*shortcut*/
bool add;
u8 *mac;
......@@ -121,14 +126,9 @@ struct bnx2x_vf_mac_vlan_filters {
/* vf context */
struct bnx2x_virtf {
u16 cfg_flags;
#define VF_CFG_STATS 0x0001
#define VF_CFG_FW_FC 0x0002
#define VF_CFG_TPA 0x0004
#define VF_CFG_INT_SIMD 0x0008
#define VF_CACHE_LINE 0x0010
#define VF_CFG_VLAN 0x0020
#define VF_CFG_STATS_COALESCE 0x0040
#define VF_CFG_EXT_BULLETIN 0x0080
#define VF_CFG_STATS_COALESCE 0x1
#define VF_CFG_EXT_BULLETIN 0x2
#define VF_CFG_VLAN_FILTER 0x4
u8 link_cfg; /* IFLA_VF_LINK_STATE_AUTO
* IFLA_VF_LINK_STATE_ENABLE
* IFLA_VF_LINK_STATE_DISABLE
......@@ -142,9 +142,8 @@ struct bnx2x_virtf {
bool flr_clnup_stage; /* true during flr cleanup */
/* dma */
dma_addr_t fw_stat_map; /* valid iff VF_CFG_STATS */
dma_addr_t fw_stat_map;
u16 stats_stride;
dma_addr_t spq_map;
dma_addr_t bulletin_map;
/* Allocated resources counters. Before the VF is acquired, the
......@@ -165,8 +164,6 @@ struct bnx2x_virtf {
#define vf_mac_rules_cnt(vf) ((vf)->alloc_resc.num_mac_filters)
#define vf_vlan_rules_cnt(vf) ((vf)->alloc_resc.num_vlan_filters)
#define vf_mc_rules_cnt(vf) ((vf)->alloc_resc.num_mc_filters)
/* Hide a single vlan filter credit for the hypervisor */
#define vf_vlan_rules_visible_cnt(vf) (vf_vlan_rules_cnt(vf) - 1)
u8 sb_count; /* actual number of SBs */
u8 igu_base_id; /* base igu status block id */
......@@ -209,6 +206,9 @@ struct bnx2x_virtf {
enum channel_tlvs op_current;
u8 fp_hsi;
struct bnx2x_credit_pool_obj vf_vlans_pool;
struct bnx2x_credit_pool_obj vf_macs_pool;
};
#define BNX2X_NR_VIRTFN(bp) ((bp)->vfdb->sriov.nr_virtfn)
......@@ -232,6 +232,12 @@ struct bnx2x_virtf {
#define FW_VF_HANDLE(abs_vfid) \
(abs_vfid + FW_PF_MAX_HANDLE)
#define GET_NUM_VFS_PER_PATH(bp) 64 /* use max possible value */
#define GET_NUM_VFS_PER_PF(bp) ((bp)->vfdb ? (bp)->vfdb->sriov.total \
: 0)
#define VF_MAC_CREDIT_CNT 1
#define VF_VLAN_CREDIT_CNT 2 /* VLAN0 + 'real' VLAN */
/* locking and unlocking the channel mutex */
void bnx2x_lock_vf_pf_channel(struct bnx2x *bp, struct bnx2x_virtf *vf,
enum channel_tlvs tlv);
......@@ -275,6 +281,10 @@ struct bnx2x_vf_sp {
struct eth_classify_rules_ramrod_data e2;
} vlan_rdata;
union {
struct eth_classify_rules_ramrod_data e2;
} vlan_mac_rdata;
union {
struct eth_filter_rules_ramrod_data e2;
} rx_mode_rdata;
......@@ -538,6 +548,7 @@ int bnx2x_iov_link_update_vf(struct bnx2x *bp, int idx);
int bnx2x_set_vf_link_state(struct net_device *dev, int vf, int link_state);
int bnx2x_vfpf_update_vlan(struct bnx2x *bp, u16 vid, u8 vf_qid, bool add);
#else /* CONFIG_BNX2X_SRIOV */
static inline void bnx2x_iov_set_queue_sp_obj(struct bnx2x *bp, int vf_cid,
......@@ -606,5 +617,7 @@ struct pf_vf_bulletin_content;
static inline void bnx2x_vf_bulletin_finalize(struct pf_vf_bulletin_content *bulletin,
bool support_long) {}
static inline int bnx2x_vfpf_update_vlan(struct bnx2x *bp, u16 vid, u8 vf_qid, bool add) {return 0; }
#endif /* CONFIG_BNX2X_SRIOV */
#endif /* bnx2x_sriov.h */
......@@ -70,6 +70,8 @@ struct hw_sb_info {
#define VFPF_RX_MASK_ACCEPT_ALL_UNICAST 0x00000004
#define VFPF_RX_MASK_ACCEPT_ALL_MULTICAST 0x00000008
#define VFPF_RX_MASK_ACCEPT_BROADCAST 0x00000010
#define VFPF_RX_MASK_ACCEPT_ANY_VLAN 0x00000020
#define BULLETIN_CONTENT_SIZE (sizeof(struct pf_vf_bulletin_content))
#define BULLETIN_CONTENT_LEGACY_SIZE (32)
#define BULLETIN_ATTEMPTS 5 /* crc failures before throwing towel */
......@@ -133,6 +135,7 @@ struct vfpf_acquire_tlv {
u8 fp_hsi_ver;
u8 caps;
#define VF_CAP_SUPPORT_EXT_BULLETIN (1 << 0)
#define VF_CAP_SUPPORT_VLAN_FILTER (1 << 1)
} vfdev_info;
struct vf_pf_resc_request resc_request;
......@@ -178,6 +181,8 @@ struct pfvf_acquire_resp_tlv {
#define PFVF_CAP_DHC 0x00000002
#define PFVF_CAP_TPA 0x00000004
#define PFVF_CAP_TPA_UPDATE 0x00000008
#define PFVF_CAP_VLAN_FILTER 0x00000010
char fw_ver[32];
u16 db_size;
u8 indices_per_sb;
......@@ -294,7 +299,7 @@ struct vfpf_q_mac_vlan_filter {
u32 flags;
#define VFPF_Q_FILTER_DEST_MAC_VALID 0x01
#define VFPF_Q_FILTER_VLAN_TAG_VALID 0x02
#define VFPF_Q_FILTER_SET_MAC 0x100 /* set/clear */
#define VFPF_Q_FILTER_SET 0x100 /* set/clear */
u8 mac[ETH_ALEN];
u16 vlan_tag;
};
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment