* Re: [PATCH repost] net,wireless: check against default_ethtool_ops
From: Jiri Pirko @ 2013-01-07 10:23 UTC (permalink / raw)
To: Stanislaw Gruszka
Cc: netdev-u79uwXL29TY76Z2rM5mHXA, David S. Miller, Eric Dumazet,
Ben Greear, Bjørn Mork,
linux-wireless-u79uwXL29TY76Z2rM5mHXA, Ben Hutchings
In-Reply-To: <20130107095548.GA6931-H+wXaHxf7aLQT0dZR+AlfA@public.gmane.org>
Mon, Jan 07, 2013 at 10:55:49AM CET, sgruszka-H+wXaHxf7aLQT0dZR+AlfA@public.gmane.org wrote:
>Since:
>
>commit 2c60db037034d27f8c636403355d52872da92f81
>Author: Eric Dumazet <edumazet-hpIqsD4AKlfQT0dZR+AlfA@public.gmane.org>
>Date: Sun Sep 16 09:17:26 2012 +0000
>
> net: provide a default dev->ethtool_ops
>
>wireless core does not correctly assign ethtool_ops. In order to fix
>the problem, and avoid assigning ethtool_ops on each individual cfg80211
>drivers, we check against default_ethool_ops pointer instead of NULL in
>wireless core.
>
>Signed-off-by: Stanislaw Gruszka <sgruszka-H+wXaHxf7aLQT0dZR+AlfA@public.gmane.org>
>Acked-by: Ben Hutchings <bhutchings-s/n/eUQHGBpZroRs9YW3xA@public.gmane.org>
>Cc: stable-u79uwXL29TY76Z2rM5mHXA@public.gmane.org # 3.7+
>---
>This should go directly through net tree since patch include core
>net specific changes.
>
> include/linux/netdevice.h | 2 ++
> net/core/dev.c | 3 ++-
> net/wireless/core.c | 2 +-
> 3 files changed, 5 insertions(+), 2 deletions(-)
>
>diff --git a/include/linux/netdevice.h b/include/linux/netdevice.h
>index f8eda02..c98e1c3 100644
>--- a/include/linux/netdevice.h
>+++ b/include/linux/netdevice.h
>@@ -60,6 +60,8 @@ struct wireless_dev;
> #define SET_ETHTOOL_OPS(netdev,ops) \
> ( (netdev)->ethtool_ops = (ops) )
>
>+extern const struct ethtool_ops default_ethtool_ops;
>+
> /* hardware address assignment types */
> #define NET_ADDR_PERM 0 /* address is permanent (default) */
> #define NET_ADDR_RANDOM 1 /* address is generated randomly */
>diff --git a/net/core/dev.c b/net/core/dev.c
>index c0946cb..4cd2168 100644
>--- a/net/core/dev.c
>+++ b/net/core/dev.c
>@@ -6008,7 +6008,8 @@ struct netdev_queue *dev_ingress_queue_create(struct net_device *dev)
> return queue;
> }
>
>-static const struct ethtool_ops default_ethtool_ops;
>+const struct ethtool_ops default_ethtool_ops;
>+EXPORT_SYMBOL_GPL(default_ethtool_ops);
I think that default_ethtool_ops should stay static. Wouldn't it be
nicer to introduce a helper like:
bool dev_has_default_ethtool_ops(struct net_device *dev)
{
return dev->ethtool_ops == &default_ethtool_ops;
}
>
> /**
> * alloc_netdev_mqs - allocate network device
>diff --git a/net/wireless/core.c b/net/wireless/core.c
>index 14d9904..90915d4 100644
>--- a/net/wireless/core.c
>+++ b/net/wireless/core.c
>@@ -866,7 +866,7 @@ static int cfg80211_netdev_notifier_call(struct notifier_block *nb,
> /* allow mac80211 to determine the timeout */
> wdev->ps_timeout = -1;
>
>- if (!dev->ethtool_ops)
>+ if (dev->ethtool_ops == &default_ethtool_ops)
> dev->ethtool_ops = &cfg80211_ethtool_ops;
>
> if ((wdev->iftype == NL80211_IFTYPE_STATION ||
>--
>1.7.1
>
>--
>To unsubscribe from this list: send the line "unsubscribe netdev" in
>the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
>More majordomo info at http://vger.kernel.org/majordomo-info.html
--
To unsubscribe from this list: send the line "unsubscribe linux-wireless" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
^ permalink raw reply
* Re: [PATCH 1/2] ipv6: avoid blackhole and prohibited entries upon prefix purge [v2]
From: Nicolas Dichtel @ 2013-01-07 10:25 UTC (permalink / raw)
To: Romain KUNTZ; +Cc: netdev@vger.kernel.org, Eric Dumazet, yoshfuji, davem
In-Reply-To: <2A507F9D-3D53-475F-8FA9-9E6CFEE9C97A@ipflavors.com>
Le 05/01/2013 22:44, Romain KUNTZ a écrit :
> Mobile IPv6 provokes a kernel Oops since commit 64c6d08e (ipv6:
> del unreachable route when an addr is deleted on lo), because
> ip6_route_lookup() may also return blackhole and prohibited
> entry. However, these entries have a NULL rt6i_table argument,
> which provokes an Oops in __ip6_del_rt() when trying to lock
> rt6i_table->tb6_lock.
>
> Beside, when purging a prefix, blakhole and prohibited entries
> should not be selected because they are not what we are looking
> for.
>
> We fix this by adding two new lookup flags (RT6_LOOKUP_F_NO_BLK_HOLE
> and RT6_LOOKUP_F_NO_PROHIBIT) in order to ensure that such entries
> are skipped during lookup and that the correct entry is returned.
>
> [v2]: use 'goto out;' instead of 'goto again;' to avoid unnecessary
> oprations on rt (as suggested by Eric Dumazet).
>
> Signed-off-by: Romain Kuntz <r.kuntz@ipflavors.com>
> ---
> include/net/ip6_route.h | 2 ++
> net/ipv6/addrconf.c | 4 +++-
> net/ipv6/fib6_rules.c | 4 ++++
> 3 files changed, 9 insertions(+), 1 deletions(-)
>
> diff --git a/include/net/ip6_route.h b/include/net/ip6_route.h
> index 27d8318..3c93743 100644
> --- a/include/net/ip6_route.h
> +++ b/include/net/ip6_route.h
> @@ -30,6 +30,8 @@ struct route_info {
> #define RT6_LOOKUP_F_SRCPREF_TMP 0x00000008
> #define RT6_LOOKUP_F_SRCPREF_PUBLIC 0x00000010
> #define RT6_LOOKUP_F_SRCPREF_COA 0x00000020
> +#define RT6_LOOKUP_F_NO_BLK_HOLE 0x00000040
> +#define RT6_LOOKUP_F_NO_PROHIBIT 0x00000080
>
> /*
> * rt6_srcprefs2flags() and rt6_flags2srcprefs() translate
> diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c
> index 408cac4a..1891e23 100644
> --- a/net/ipv6/addrconf.c
> +++ b/net/ipv6/addrconf.c
> @@ -948,7 +948,9 @@ static void ipv6_del_addr(struct inet6_ifaddr *ifp)
> fl6.flowi6_oif = ifp->idev->dev->ifindex;
> fl6.daddr = prefix;
> rt = (struct rt6_info *)ip6_route_lookup(net, &fl6,
> - RT6_LOOKUP_F_IFACE);
> + RT6_LOOKUP_F_IFACE |
> + RT6_LOOKUP_F_NO_BLK_HOLE |
> + RT6_LOOKUP_F_NO_PROHIBIT);
>
> if (rt != net->ipv6.ip6_null_entry &&
Is it not simpler to test the result here (net->ipv6.ip6_blk_hole_entry and
net->ipv6.ip6_prohibit_entry) like for the null_entry?
It will also avoid adding more flags.
^ permalink raw reply
* Re: [PATCH repost] net,wireless: check against default_ethtool_ops
From: Stanislaw Gruszka @ 2013-01-07 10:44 UTC (permalink / raw)
To: Jiri Pirko
Cc: netdev, David S. Miller, Eric Dumazet, Ben Greear,
Bjørn Mork, linux-wireless, Ben Hutchings
In-Reply-To: <20130107102307.GA1587@minipsycho.orion>
On Mon, Jan 07, 2013 at 11:23:07AM +0100, Jiri Pirko wrote:
> >-static const struct ethtool_ops default_ethtool_ops;
> >+const struct ethtool_ops default_ethtool_ops;
> >+EXPORT_SYMBOL_GPL(default_ethtool_ops);
>
> I think that default_ethtool_ops should stay static. Wouldn't it be
> nicer to introduce a helper like:
>
> bool dev_has_default_ethtool_ops(struct net_device *dev)
> {
> return dev->ethtool_ops == &default_ethtool_ops;
> }
Then I still have to export this function. So with your approch, number
of exported symbols will be the same, but there will be few more lines
of code.
Stanislaw
^ permalink raw reply
* [PATCH net-next] bnx2x: Segregate SR-IOV code
From: Ariel Elior @ 2013-01-07 10:50 UTC (permalink / raw)
To: David Miller
In this patch the SR-IOV code is segregated from the main bulk of
the bnx2x code. The CONFIG_BNX2X_SRIOV define is added to Broadcom's
Kconfig, and allows the elision of the building of all the SR-IOV
support code in the driver.
The define is dependant on the kernel CONFIG_PCI_IOV configuration
define.
Signed-off-by: Ariel Elior <ariele@broadcom.com>
---
drivers/net/ethernet/broadcom/Kconfig | 9 +
drivers/net/ethernet/broadcom/bnx2x/Makefile | 3 +-
drivers/net/ethernet/broadcom/bnx2x/bnx2x.h | 20 +-
drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c | 92 +---
drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.h | 18 +-
drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c | 729 +--------------------
drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c | 208 ++++++-
drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.h | 97 +++-
drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.c | 618 +++++++++++++++++-
drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.h | 3 +
10 files changed, 953 insertions(+), 844 deletions(-)
diff --git a/drivers/net/ethernet/broadcom/Kconfig b/drivers/net/ethernet/broadcom/Kconfig
index f552673..3b3bf0d 100644
--- a/drivers/net/ethernet/broadcom/Kconfig
+++ b/drivers/net/ethernet/broadcom/Kconfig
@@ -121,4 +121,13 @@ config BNX2X
To compile this driver as a module, choose M here: the module
will be called bnx2x. This is recommended.
+config BNX2X_SRIOV
+ bool "Broadcom 578xx and 57712 SR-IOV support"
+ depends on BNX2X && PCI_IOV
+ default y
+ ---help---
+ This configuration parameter enables Single Root Input Output
+ Virtualization support in the 578xx and 57712 products. This
+ allows for virtual function acceleration in virtual environments.
+
endif # NET_VENDOR_BROADCOM
diff --git a/drivers/net/ethernet/broadcom/bnx2x/Makefile b/drivers/net/ethernet/broadcom/bnx2x/Makefile
index 2ef6803..116762d 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/Makefile
+++ b/drivers/net/ethernet/broadcom/bnx2x/Makefile
@@ -4,4 +4,5 @@
obj-$(CONFIG_BNX2X) += bnx2x.o
-bnx2x-objs := bnx2x_main.o bnx2x_link.o bnx2x_cmn.o bnx2x_ethtool.o bnx2x_stats.o bnx2x_dcb.o bnx2x_sp.o bnx2x_vfpf.o bnx2x_sriov.o
+bnx2x-y := bnx2x_main.o bnx2x_link.o bnx2x_cmn.o bnx2x_ethtool.o bnx2x_stats.o bnx2x_dcb.o bnx2x_sp.o
+bnx2x-$(CONFIG_BNX2X_SRIOV) += bnx2x_vfpf.o bnx2x_sriov.o
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x.h b/drivers/net/ethernet/broadcom/bnx2x/bnx2x.h
index 8596917..02c93e3 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x.h
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x.h
@@ -1266,6 +1266,7 @@ struct bnx2x {
(vn) * ((CHIP_IS_E1x(bp) || (CHIP_MODE_IS_4_PORT(bp))) ? 2 : 1))
#define BP_FW_MB_IDX(bp) BP_FW_MB_IDX_VN(bp, BP_VN(bp))
+#ifdef CONFIG_BNX2X_SRIOV
/* vf pf channel mailbox contains request and response buffers */
struct bnx2x_vf_mbx_msg *vf2pf_mbox;
dma_addr_t vf2pf_mbox_mapping;
@@ -1278,6 +1279,7 @@ struct bnx2x {
dma_addr_t pf2vf_bulletin_mapping;
struct pf_vf_bulletin_content old_bulletin;
+#endif /* CONFIG_BNX2X_SRIOV */
struct net_device *dev;
struct pci_dev *pdev;
@@ -1379,8 +1381,14 @@ struct bnx2x {
#define IS_VF_FLAG (1 << 22)
#define BP_NOMCP(bp) ((bp)->flags & NO_MCP_FLAG)
+
+#ifdef CONFIG_BNX2X_SRIOV
#define IS_VF(bp) ((bp)->flags & IS_VF_FLAG)
#define IS_PF(bp) (!((bp)->flags & IS_VF_FLAG))
+#else
+#define IS_VF(bp) false
+#define IS_PF(bp) true
+#endif
#define NO_ISCSI(bp) ((bp)->flags & NO_ISCSI_FLAG)
#define NO_ISCSI_OOO(bp) ((bp)->flags & NO_ISCSI_OOO_FLAG)
@@ -2275,18 +2283,6 @@ void bnx2x_igu_clear_sb_gen(struct bnx2x *bp, u8 func, u8 idu_sb_id,
#define GOOD_ME_REG(me_reg) (((me_reg) & ME_REG_VF_VALID) && \
(!((me_reg) & ME_REG_VF_ERR)))
-int bnx2x_get_vf_id(struct bnx2x *bp, u32 *vf_id);
-int bnx2x_send_msg2pf(struct bnx2x *bp, u8 *done, dma_addr_t msg_mapping);
-int bnx2x_vfpf_acquire(struct bnx2x *bp, u8 tx_count, u8 rx_count);
-int bnx2x_vfpf_release(struct bnx2x *bp);
-int bnx2x_vfpf_init(struct bnx2x *bp);
-void bnx2x_vfpf_close_vf(struct bnx2x *bp);
-int bnx2x_vfpf_setup_q(struct bnx2x *bp, int fp_idx);
-int bnx2x_vfpf_teardown_queue(struct bnx2x *bp, int qidx);
-int bnx2x_vfpf_set_mac(struct bnx2x *bp);
-int bnx2x_vfpf_set_mcast(struct net_device *dev);
-int bnx2x_vfpf_storm_rx_mode(struct bnx2x *bp);
-
int bnx2x_nic_load_analyze_req(struct bnx2x *bp, u32 load_code);
/* Congestion management fairness mode */
#define CMNG_FNS_NONE 0
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c
index f9a15cb..1437f7e 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.c
@@ -27,7 +27,6 @@
#include "bnx2x_cmn.h"
#include "bnx2x_init.h"
#include "bnx2x_sp.h"
-#include "bnx2x_sriov.h"
/**
* bnx2x_move_fp - move content of the fastpath structure.
@@ -109,7 +108,7 @@ void bnx2x_fill_fw_str(struct bnx2x *bp, char *buf, size_t buf_len)
(bp->common.bc_ver & 0xff),
((phy_fw_ver[0] != '\0') ? " phy " : ""), phy_fw_ver);
} else {
- strlcpy(buf, bp->acquire_resp.pfdev_info.fw_ver, buf_len);
+ bnx2x_vf_fill_fw_str(bp, buf, buf_len);
}
}
@@ -2048,7 +2047,7 @@ static int bnx2x_alloc_fw_stats_mem(struct bnx2x *bp)
* request struct
*/
if (IS_SRIOV(bp))
- vf_headroom = bp->vfdb->sriov.nr_virtfn * BNX2X_CLIENTS_PER_VF;
+ vf_headroom = bnx2x_vf_headroom(bp);
/* Request is built from stats_query_header and an array of
* stats_query_cmd_group each of which contains
@@ -3793,93 +3792,6 @@ int bnx2x_setup_tc(struct net_device *dev, u8 num_tc)
return 0;
}
-/* New mac for VF. Consider these cases:
- * 1. VF hasn't been acquired yet - save the mac in local bulletin board and
- * supply at acquire.
- * 2. VF has already been acquired but has not yet initialized - store in local
- * bulletin board. mac will be posted on VF bulletin board after VF init. VF
- * will configure this mac when it is ready.
- * 3. VF has already initialized but has not yet setup a queue - post the new
- * mac on VF's bulletin board right now. VF will configure this mac when it
- * is ready.
- * 4. VF has already set a queue - delete any macs already configured for this
- * queue and manually config the new mac.
- * In any event, once this function has been called refuse any attempts by the
- * VF to configure any mac for itself except for this mac. In case of a race
- * where the VF fails to see the new post on its bulletin board before sending a
- * mac configuration request, the PF will simply fail the request and VF can try
- * again after consulting its bulletin board
- */
-int bnx2x_set_vf_mac(struct net_device *dev, int queue, u8 *mac)
-{
- struct bnx2x *bp = netdev_priv(dev);
- int rc, q_logical_state, vfidx = queue;
- struct bnx2x_virtf *vf = BP_VF(bp, vfidx);
- struct pf_vf_bulletin_content *bulletin = BP_VF_BULLETIN(bp, vfidx);
-
- /* if SRIOV is disabled there is nothing to do (and somewhere, someone
- * has erred).
- */
- if (!IS_SRIOV(bp)) {
- BNX2X_ERR("bnx2x_set_vf_mac called though sriov is disabled\n");
- return -EINVAL;
- }
-
- if (!is_valid_ether_addr(mac)) {
- BNX2X_ERR("mac address invalid\n");
- return -EINVAL;
- }
-
- /* update PF's copy of the VF's bulletin. will no longer accept mac
- * configuration requests from vf unless match this mac
- */
- bulletin->valid_bitmap |= 1 << MAC_ADDR_VALID;
- memcpy(bulletin->mac, mac, ETH_ALEN);
-
- /* Post update on VF's bulletin board */
- rc = bnx2x_post_vf_bulletin(bp, vfidx);
- if (rc) {
- BNX2X_ERR("failed to update VF[%d] bulletin\n", vfidx);
- return rc;
- }
-
- /* is vf initialized and queue set up? */
- q_logical_state =
- bnx2x_get_q_logical_state(bp, &bnx2x_vfq(vf, 0, sp_obj));
- if (vf->state == VF_ENABLED &&
- q_logical_state == BNX2X_Q_LOGICAL_STATE_ACTIVE) {
- /* configure the mac in device on this vf's queue */
- unsigned long flags = 0;
- struct bnx2x_vlan_mac_obj *mac_obj = &bnx2x_vfq(vf, 0, mac_obj);
-
- /* must lock vfpf channel to protect against vf flows */
- bnx2x_lock_vf_pf_channel(bp, vf, CHANNEL_TLV_PF_SET_MAC);
-
- /* remove existing eth macs */
- rc = bnx2x_del_all_macs(bp, mac_obj, BNX2X_ETH_MAC, true);
- if (rc) {
- BNX2X_ERR("failed to delete eth macs\n");
- return -EINVAL;
- }
-
- /* remove existing uc list macs */
- rc = bnx2x_del_all_macs(bp, mac_obj, BNX2X_UC_LIST_MAC, true);
- if (rc) {
- BNX2X_ERR("failed to delete uc_list macs\n");
- return -EINVAL;
- }
-
- /* configure the new mac to device */
- __set_bit(RAMROD_COMP_WAIT, &flags);
- bnx2x_set_mac_one(bp, (u8 *)&bulletin->mac, mac_obj, true,
- BNX2X_ETH_MAC, &flags);
-
- bnx2x_unlock_vf_pf_channel(bp, vf, CHANNEL_TLV_PF_SET_MAC);
- }
-
- return rc;
-}
-
/* called with rtnl_lock */
int bnx2x_change_mac_addr(struct net_device *dev, void *p)
{
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.h b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.h
index 23a1fa9..6667ec5 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.h
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_cmn.h
@@ -24,6 +24,7 @@
#include "bnx2x.h"
+#include "bnx2x_sriov.h"
/* This is used as a replacement for an MCP if it's not present */
extern int load_count[2][3]; /* per-path: 0-common, 1-port0, 2-port1 */
@@ -1128,22 +1129,7 @@ static inline u8 bnx2x_fp_qzone_id(struct bnx2x_fastpath *fp)
return fp->cl_id;
}
-static inline u32 bnx2x_rx_ustorm_prods_offset(struct bnx2x_fastpath *fp)
-{
- struct bnx2x *bp = fp->bp;
- u32 offset = BAR_USTRORM_INTMEM;
-
- if (IS_VF(bp))
- return PXP_VF_ADDR_USDM_QUEUES_START +
- bp->acquire_resp.resc.hw_qid[fp->index] *
- sizeof(struct ustorm_queue_zone_data);
- else if (!CHIP_IS_E1x(bp))
- offset += USTORM_RX_PRODS_E2_OFFSET(fp->cl_qzone_id);
- else
- offset += USTORM_RX_PRODS_E1X_OFFSET(BP_PORT(bp), fp->cl_id);
-
- return offset;
-}
+u32 bnx2x_rx_ustorm_prods_offset(struct bnx2x_fastpath *fp);
static inline void bnx2x_init_txdata(struct bnx2x *bp,
struct bnx2x_fp_txdata *txdata, u32 cid,
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c
index 2b6a919..5fcaee1 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_main.c
@@ -60,7 +60,6 @@
#include "bnx2x_init_ops.h"
#include "bnx2x_cmn.h"
#include "bnx2x_vfpf.h"
-#include "bnx2x_sriov.h"
#include "bnx2x_dcb.h"
#include "bnx2x_sp.h"
@@ -5269,62 +5268,6 @@ void bnx2x_drv_pulse(struct bnx2x *bp)
bp->fw_drv_pulse_wr_seq);
}
-/* crc is the first field in the bulletin board. compute the crc over the
- * entire bulletin board excluding the crc field itself
- */
-u32 bnx2x_crc_vf_bulletin(struct bnx2x *bp,
- struct pf_vf_bulletin_content *bulletin)
-{
- return crc32(BULLETIN_CRC_SEED,
- ((u8 *)bulletin) + sizeof(bulletin->crc),
- BULLETIN_CONTENT_SIZE - sizeof(bulletin->crc));
-}
-
-/* Check for new posts on the bulletin board */
-enum sample_bulletin_result bnx2x_sample_bulletin(struct bnx2x *bp)
-{
- struct pf_vf_bulletin_content bulletin = bp->pf2vf_bulletin->content;
- int attempts;
-
- /* bulletin board hasn't changed since last sample */
- if (bp->old_bulletin.version == bulletin.version)
- return PFVF_BULLETIN_UNCHANGED;
-
- /* validate crc of new bulletin board */
- if (bp->old_bulletin.version != bp->pf2vf_bulletin->content.version) {
- /* sampling structure in mid post may result with corrupted data
- * validate crc to ensure coherency.
- */
- for (attempts = 0; attempts < BULLETIN_ATTEMPTS; attempts++) {
- bulletin = bp->pf2vf_bulletin->content;
- if (bulletin.crc == bnx2x_crc_vf_bulletin(bp,
- &bulletin))
- break;
-
- BNX2X_ERR("bad crc on bulletin board. contained %x computed %x\n",
- bulletin.crc,
- bnx2x_crc_vf_bulletin(bp, &bulletin));
- }
- if (attempts >= BULLETIN_ATTEMPTS) {
- BNX2X_ERR("pf to vf bulletin board crc was wrong %d consecutive times. Aborting\n",
- attempts);
- return PFVF_BULLETIN_CRC_ERR;
- }
- }
-
- /* the mac address in bulletin board is valid and is new */
- if (bulletin.valid_bitmap & 1 << MAC_ADDR_VALID &&
- memcmp(bulletin.mac, bp->old_bulletin.mac, ETH_ALEN)) {
- /* update new mac to net device */
- memcpy(bp->dev->dev_addr, bulletin.mac, ETH_ALEN);
- }
-
- /* copy new bulletin board to bp */
- bp->old_bulletin = bulletin;
-
- return PFVF_BULLETIN_UPDATED;
-}
-
static void bnx2x_timer(unsigned long data)
{
struct bnx2x *bp = (struct bnx2x *) data;
@@ -9525,29 +9468,14 @@ sp_rtnl_not_reset:
/* work which needs rtnl lock not-taken (as it takes the lock itself and
* can be called from other contexts as well)
*/
-
rtnl_unlock();
+ /* enable SR-IOV if applicable */
if (IS_SRIOV(bp) && test_and_clear_bit(BNX2X_SP_RTNL_ENABLE_SRIOV,
- &bp->sp_rtnl_state)) {
- int rc = 0;
-
- /* disbale sriov in case it is still enabled */
- pci_disable_sriov(bp->pdev);
- DP(BNX2X_MSG_IOV, "sriov disabled\n");
-
- /* enable sriov */
- DP(BNX2X_MSG_IOV, "vf num (%d)\n", (bp->vfdb->sriov.nr_virtfn));
- rc = pci_enable_sriov(bp->pdev, (bp->vfdb->sriov.nr_virtfn));
- if (rc)
- BNX2X_ERR("pci_enable_sriov failed with %d\n", rc);
- else
- DP(BNX2X_MSG_IOV, "sriov enabled\n");
- }
+ &bp->sp_rtnl_state))
+ bnx2x_enable_sriov(bp);
}
-/* end of nic load/unload */
-
static void bnx2x_period_task(struct work_struct *work)
{
struct bnx2x *bp = container_of(work, struct bnx2x, period_task.work);
@@ -11790,7 +11718,9 @@ static const struct net_device_ops bnx2x_netdev_ops = {
.ndo_poll_controller = poll_bnx2x,
#endif
.ndo_setup_tc = bnx2x_setup_tc,
+#ifdef CONFIG_BNX2X_SRIOV
.ndo_set_vf_mac = bnx2x_set_vf_mac,
+#endif
#ifdef NETDEV_FCOE_WWNN
.ndo_fcoe_get_wwn = bnx2x_fcoe_get_wwn,
#endif
@@ -12445,17 +12375,10 @@ static int bnx2x_init_one(struct pci_dev *pdev,
* l2 connections.
*/
if (IS_VF(bp)) {
- /* vf doorbells are embedded within the regview */
- bp->doorbells = bp->regview + PXP_VF_ADDR_DB_START;
-
- /* allocate vf2pf mailbox for vf to pf channel */
- BNX2X_PCI_ALLOC(bp->vf2pf_mbox, &bp->vf2pf_mbox_mapping,
- sizeof(struct bnx2x_vf_mbx_msg));
-
- /* allocate pf 2 vf bulletin board */
- BNX2X_PCI_ALLOC(bp->pf2vf_bulletin, &bp->pf2vf_bulletin_mapping,
- sizeof(union pf_vf_bulletin));
-
+ bnx2x_vf_map_doorbells(bp);
+ rc = bnx2x_vf_pci_alloc(bp);
+ if (rc)
+ goto init_one_exit;
} else {
doorbell_size = BNX2X_L2_MAX_CID(bp) * (1 << BNX2X_DB_SHIFT);
if (doorbell_size > pci_resource_len(pdev, 2)) {
@@ -12552,11 +12475,6 @@ static int bnx2x_init_one(struct pci_dev *pdev,
return 0;
-alloc_mem_err:
- BNX2X_PCI_FREE(bp->vf2pf_mbox, bp->vf2pf_mbox_mapping,
- sizeof(struct bnx2x_vf_mbx_msg));
- rc = -ENOMEM;
-
init_one_exit:
if (bp->regview)
iounmap(bp->regview);
@@ -13419,619 +13337,36 @@ struct cnic_eth_dev *bnx2x_cnic_probe(struct net_device *dev)
return cp;
}
-int bnx2x_send_msg2pf(struct bnx2x *bp, u8 *done, dma_addr_t msg_mapping)
-{
- struct cstorm_vf_zone_data __iomem *zone_data =
- REG_ADDR(bp, PXP_VF_ADDR_CSDM_GLOBAL_START);
- int tout = 600, interval = 100; /* wait for 60 seconds */
-
- if (*done) {
- BNX2X_ERR("done was non zero before message to pf was sent\n");
- WARN_ON(true);
- return -EINVAL;
- }
-
- /* Write message address */
- writel(U64_LO(msg_mapping),
- &zone_data->non_trigger.vf_pf_channel.msg_addr_lo);
- writel(U64_HI(msg_mapping),
- &zone_data->non_trigger.vf_pf_channel.msg_addr_hi);
-
- /* make sure the address is written before FW accesses it */
- wmb();
-
- /* Trigger the PF FW */
- writeb(1, &zone_data->trigger.vf_pf_channel.addr_valid);
-
- /* Wait for PF to complete */
- while ((tout >= 0) && (!*done)) {
- msleep(interval);
- tout -= 1;
-
- /* progress indicator - HV can take its own sweet time in
- * answering VFs...
- */
- DP_CONT(BNX2X_MSG_IOV, ".");
- }
-
- if (!*done) {
- BNX2X_ERR("PF response has timed out\n");
- return -EAGAIN;
- }
- DP(BNX2X_MSG_SP, "Got a response from PF\n");
- return 0;
-}
-
-int bnx2x_get_vf_id(struct bnx2x *bp, u32 *vf_id)
-{
- u32 me_reg;
- int tout = 10, interval = 100; /* Wait for 1 sec */
-
- do {
- /* pxp traps vf read of doorbells and returns me reg value */
- me_reg = readl(bp->doorbells);
- if (GOOD_ME_REG(me_reg))
- break;
-
- msleep(interval);
-
- BNX2X_ERR("Invalid ME register value: 0x%08x\n. Is pf driver up?",
- me_reg);
- } while (tout-- > 0);
-
- if (!GOOD_ME_REG(me_reg)) {
- BNX2X_ERR("Invalid ME register value: 0x%08x\n", me_reg);
- return -EINVAL;
- }
-
- BNX2X_ERR("valid ME register value: 0x%08x\n", me_reg);
-
- *vf_id = (me_reg & ME_REG_VF_NUM_MASK) >> ME_REG_VF_NUM_SHIFT;
-
- return 0;
-}
-
-int bnx2x_vfpf_acquire(struct bnx2x *bp, u8 tx_count, u8 rx_count)
-{
- int rc = 0, attempts = 0;
- struct vfpf_acquire_tlv *req = &bp->vf2pf_mbox->req.acquire;
- struct pfvf_acquire_resp_tlv *resp = &bp->vf2pf_mbox->resp.acquire_resp;
- u32 vf_id;
- bool resources_acquired = false;
-
- /* clear mailbox and prep first tlv */
- bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_ACQUIRE, sizeof(*req));
-
- if (bnx2x_get_vf_id(bp, &vf_id))
- return -EAGAIN;
-
- req->vfdev_info.vf_id = vf_id;
- req->vfdev_info.vf_os = 0;
-
- req->resc_request.num_rxqs = rx_count;
- req->resc_request.num_txqs = tx_count;
- req->resc_request.num_sbs = bp->igu_sb_cnt;
- req->resc_request.num_mac_filters = VF_ACQUIRE_MAC_FILTERS;
- req->resc_request.num_mc_filters = VF_ACQUIRE_MC_FILTERS;
-
- /* pf 2 vf bulletin board address */
- req->bulletin_addr = bp->pf2vf_bulletin_mapping;
-
- /* add list termination tlv */
- bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
- sizeof(struct channel_list_end_tlv));
-
- /* output tlvs list */
- bnx2x_dp_tlv_list(bp, req);
-
- while (!resources_acquired) {
- DP(BNX2X_MSG_SP, "attempting to acquire resources\n");
-
- /* send acquire request */
- rc = bnx2x_send_msg2pf(bp,
- &resp->hdr.status,
- bp->vf2pf_mbox_mapping);
-
- /* PF timeout */
- if (rc)
- return rc;
-
- /* copy acquire response from buffer to bp */
- memcpy(&bp->acquire_resp, resp, sizeof(bp->acquire_resp));
-
- attempts++;
-
- /* test whether the PF accepted our request. If not, humble the
- * the request and try again.
- */
- if (bp->acquire_resp.hdr.status == PFVF_STATUS_SUCCESS) {
- DP(BNX2X_MSG_SP, "resources acquired\n");
- resources_acquired = true;
- } else if (bp->acquire_resp.hdr.status ==
- PFVF_STATUS_NO_RESOURCE &&
- attempts < VF_ACQUIRE_THRESH) {
- DP(BNX2X_MSG_SP,
- "PF unwilling to fulfill resource request. Try PF recommended amount\n");
-
- /* humble our request */
- req->resc_request.num_txqs =
- bp->acquire_resp.resc.num_txqs;
- req->resc_request.num_rxqs =
- bp->acquire_resp.resc.num_rxqs;
- req->resc_request.num_sbs =
- bp->acquire_resp.resc.num_sbs;
- req->resc_request.num_mac_filters =
- bp->acquire_resp.resc.num_mac_filters;
- req->resc_request.num_vlan_filters =
- bp->acquire_resp.resc.num_vlan_filters;
- req->resc_request.num_mc_filters =
- bp->acquire_resp.resc.num_mc_filters;
-
- /* Clear response buffer */
- memset(&bp->vf2pf_mbox->resp, 0,
- sizeof(union pfvf_tlvs));
- } else {
- /* PF reports error */
- BNX2X_ERR("Failed to get the requested amount of resources: %d. Breaking...\n",
- bp->acquire_resp.hdr.status);
- return -EAGAIN;
- }
- }
-
- /* get HW info */
- bp->common.chip_id |= (bp->acquire_resp.pfdev_info.chip_num & 0xffff);
- bp->link_params.chip_id = bp->common.chip_id;
- bp->db_size = bp->acquire_resp.pfdev_info.db_size;
- bp->common.int_block = INT_BLOCK_IGU;
- bp->common.chip_port_mode = CHIP_2_PORT_MODE;
- bp->igu_dsb_id = -1;
- bp->mf_ov = 0;
- bp->mf_mode = 0;
- bp->common.flash_size = 0;
- bp->flags |=
- NO_WOL_FLAG | NO_ISCSI_OOO_FLAG | NO_ISCSI_FLAG | NO_FCOE_FLAG;
- bp->igu_sb_cnt = 1;
- bp->igu_base_sb = bp->acquire_resp.resc.hw_sbs[0].hw_sb_id;
- strlcpy(bp->fw_ver, bp->acquire_resp.pfdev_info.fw_ver,
- sizeof(bp->fw_ver));
-
- if (is_valid_ether_addr(bp->acquire_resp.resc.current_mac_addr))
- memcpy(bp->dev->dev_addr,
- bp->acquire_resp.resc.current_mac_addr,
- ETH_ALEN);
-
- return 0;
-}
-
-int bnx2x_vfpf_release(struct bnx2x *bp)
-{
- struct vfpf_release_tlv *req = &bp->vf2pf_mbox->req.release;
- struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
- u32 rc = 0, vf_id;
-
- /* clear mailbox and prep first tlv */
- bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_RELEASE, sizeof(*req));
-
- if (bnx2x_get_vf_id(bp, &vf_id))
- return -EAGAIN;
-
- req->vf_id = vf_id;
-
- /* add list termination tlv */
- bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
- sizeof(struct channel_list_end_tlv));
-
- /* output tlvs list */
- bnx2x_dp_tlv_list(bp, req);
-
- /* send release request */
- rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
-
- if (rc)
- /* PF timeout */
- return rc;
- if (resp->hdr.status == PFVF_STATUS_SUCCESS) {
- /* PF released us */
- DP(BNX2X_MSG_SP, "vf released\n");
- } else {
- /* PF reports error */
- BNX2X_ERR("PF failed our release request - are we out of sync? response status: %d\n",
- resp->hdr.status);
- return -EAGAIN;
- }
-
- return 0;
-}
-
-/* Tell PF about SB addresses */
-int bnx2x_vfpf_init(struct bnx2x *bp)
-{
- struct vfpf_init_tlv *req = &bp->vf2pf_mbox->req.init;
- struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
- int rc, i;
-
- /* clear mailbox and prep first tlv */
- bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_INIT, sizeof(*req));
-
- /* status blocks */
- for_each_eth_queue(bp, i)
- req->sb_addr[i] = (dma_addr_t)bnx2x_fp(bp, i,
- status_blk_mapping);
-
- /* statistics - requests only supports single queue for now */
- req->stats_addr = bp->fw_stats_data_mapping +
- offsetof(struct bnx2x_fw_stats_data, queue_stats);
-
- /* add list termination tlv */
- bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
- sizeof(struct channel_list_end_tlv));
-
- /* output tlvs list */
- bnx2x_dp_tlv_list(bp, req);
-
- rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
- if (rc)
- return rc;
-
- if (resp->hdr.status != PFVF_STATUS_SUCCESS) {
- BNX2X_ERR("INIT VF failed: %d. Breaking...\n",
- resp->hdr.status);
- return -EAGAIN;
- }
-
- DP(BNX2X_MSG_SP, "INIT VF Succeeded\n");
- return 0;
-}
-
-/* CLOSE VF - opposite to INIT_VF */
-void bnx2x_vfpf_close_vf(struct bnx2x *bp)
-{
- struct vfpf_close_tlv *req = &bp->vf2pf_mbox->req.close;
- struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
- int i, rc;
- u32 vf_id;
-
- /* If we haven't got a valid VF id, there is no sense to
- * continue with sending messages
- */
- if (bnx2x_get_vf_id(bp, &vf_id))
- goto free_irq;
-
- /* Close the queues */
- for_each_queue(bp, i)
- bnx2x_vfpf_teardown_queue(bp, i);
-
- /* clear mailbox and prep first tlv */
- bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_CLOSE, sizeof(*req));
-
- req->vf_id = vf_id;
-
- /* add list termination tlv */
- bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
- sizeof(struct channel_list_end_tlv));
-
- /* output tlvs list */
- bnx2x_dp_tlv_list(bp, req);
-
- rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
-
- if (rc)
- BNX2X_ERR("Sending CLOSE failed. rc was: %d\n", rc);
-
- else if (resp->hdr.status != PFVF_STATUS_SUCCESS)
- BNX2X_ERR("Sending CLOSE failed: pf response was %d\n",
- resp->hdr.status);
-
-free_irq:
- /* Disable HW interrupts, NAPI */
- bnx2x_netif_stop(bp, 0);
- /* Delete all NAPI objects */
- bnx2x_del_all_napi(bp);
-
- /* Release IRQs */
- bnx2x_free_irq(bp);
-}
-
-/* ask the pf to open a queue for the vf */
-int bnx2x_vfpf_setup_q(struct bnx2x *bp, int fp_idx)
-{
- struct vfpf_setup_q_tlv *req = &bp->vf2pf_mbox->req.setup_q;
- struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
- struct bnx2x_fastpath *fp = &bp->fp[fp_idx];
- u16 tpa_agg_size = 0, flags = 0;
- int rc;
-
- /* clear mailbox and prep first tlv */
- bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_SETUP_Q, sizeof(*req));
-
- /* select tpa mode to request */
- if (!fp->disable_tpa) {
- flags |= VFPF_QUEUE_FLG_TPA;
- flags |= VFPF_QUEUE_FLG_TPA_IPV6;
- if (fp->mode == TPA_MODE_GRO)
- flags |= VFPF_QUEUE_FLG_TPA_GRO;
- tpa_agg_size = TPA_AGG_SIZE;
- }
-
- /* calculate queue flags */
- flags |= VFPF_QUEUE_FLG_STATS;
- flags |= VFPF_QUEUE_FLG_CACHE_ALIGN;
- flags |= IS_MF_SD(bp) ? VFPF_QUEUE_FLG_OV : 0;
- flags |= VFPF_QUEUE_FLG_VLAN;
- DP(NETIF_MSG_IFUP, "vlan removal enabled\n");
-
- /* Common */
- req->vf_qid = fp_idx;
- req->param_valid = VFPF_RXQ_VALID | VFPF_TXQ_VALID;
-
- /* Rx */
- req->rxq.rcq_addr = fp->rx_comp_mapping;
- req->rxq.rcq_np_addr = fp->rx_comp_mapping + BCM_PAGE_SIZE;
- req->rxq.rxq_addr = fp->rx_desc_mapping;
- req->rxq.sge_addr = fp->rx_sge_mapping;
- req->rxq.vf_sb = fp_idx;
- req->rxq.sb_index = HC_INDEX_ETH_RX_CQ_CONS;
- req->rxq.hc_rate = bp->rx_ticks ? 1000000/bp->rx_ticks : 0;
- req->rxq.mtu = bp->dev->mtu;
- req->rxq.buf_sz = fp->rx_buf_size;
- req->rxq.sge_buf_sz = BCM_PAGE_SIZE * PAGES_PER_SGE;
- req->rxq.tpa_agg_sz = tpa_agg_size;
- req->rxq.max_sge_pkt = SGE_PAGE_ALIGN(bp->dev->mtu) >> SGE_PAGE_SHIFT;
- req->rxq.max_sge_pkt = ((req->rxq.max_sge_pkt + PAGES_PER_SGE - 1) &
- (~(PAGES_PER_SGE-1))) >> PAGES_PER_SGE_SHIFT;
- req->rxq.flags = flags;
- req->rxq.drop_flags = 0;
- req->rxq.cache_line_log = BNX2X_RX_ALIGN_SHIFT;
- req->rxq.stat_id = -1; /* No stats at the moment */
-
- /* Tx */
- req->txq.txq_addr = fp->txdata_ptr[FIRST_TX_COS_INDEX]->tx_desc_mapping;
- req->txq.vf_sb = fp_idx;
- req->txq.sb_index = HC_INDEX_ETH_TX_CQ_CONS_COS0;
- req->txq.hc_rate = bp->tx_ticks ? 1000000/bp->tx_ticks : 0;
- req->txq.flags = flags;
- req->txq.traffic_type = LLFC_TRAFFIC_TYPE_NW;
-
- /* add list termination tlv */
- bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
- sizeof(struct channel_list_end_tlv));
-
- /* output tlvs list */
- bnx2x_dp_tlv_list(bp, req);
-
- rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
- if (rc)
- BNX2X_ERR("Sending SETUP_Q message for queue[%d] failed!\n",
- fp_idx);
-
- if (resp->hdr.status != PFVF_STATUS_SUCCESS) {
- BNX2X_ERR("Status of SETUP_Q for queue[%d] is %d\n",
- fp_idx, resp->hdr.status);
- return -EINVAL;
- }
- return rc;
-}
-
-int bnx2x_vfpf_teardown_queue(struct bnx2x *bp, int qidx)
+u32 bnx2x_rx_ustorm_prods_offset(struct bnx2x_fastpath *fp)
{
- struct vfpf_q_op_tlv *req = &bp->vf2pf_mbox->req.q_op;
- struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
- int rc;
-
- /* clear mailbox and prep first tlv */
- bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_TEARDOWN_Q,
- sizeof(*req));
-
- req->vf_qid = qidx;
-
- /* add list termination tlv */
- bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
- sizeof(struct channel_list_end_tlv));
-
- /* output tlvs list */
- bnx2x_dp_tlv_list(bp, req);
-
- rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
-
- if (rc) {
- BNX2X_ERR("Sending TEARDOWN for queue %d failed: %d\n", qidx,
- rc);
- return rc;
- }
-
- /* PF failed the transaction */
- if (resp->hdr.status != PFVF_STATUS_SUCCESS) {
- BNX2X_ERR("TEARDOWN for queue %d failed: %d\n", qidx,
- resp->hdr.status);
- return -EINVAL;
- }
-
- return 0;
-}
-
-/* request pf to add a mac for the vf */
-int bnx2x_vfpf_set_mac(struct bnx2x *bp)
-{
- struct vfpf_set_q_filters_tlv *req = &bp->vf2pf_mbox->req.set_q_filters;
- struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
- int rc;
-
- /* clear mailbox and prep first tlv */
- bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_SET_Q_FILTERS,
- sizeof(*req));
-
- req->flags = VFPF_SET_Q_FILTERS_MAC_VLAN_CHANGED;
- req->vf_qid = 0;
- req->n_mac_vlan_filters = 1;
- req->filters[0].flags =
- VFPF_Q_FILTER_DEST_MAC_VALID | VFPF_Q_FILTER_SET_MAC;
-
- /* sample bulletin board for new mac */
- bnx2x_sample_bulletin(bp);
-
- /* copy mac from device to request */
- memcpy(req->filters[0].mac, bp->dev->dev_addr, ETH_ALEN);
-
- /* add list termination tlv */
- bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
- sizeof(struct channel_list_end_tlv));
-
- /* output tlvs list */
- bnx2x_dp_tlv_list(bp, req);
-
- /* send message to pf */
- rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
- if (rc) {
- BNX2X_ERR("failed to send message to pf. rc was %d\n", rc);
- return rc;
- }
-
- /* failure may mean PF was configured with a new mac for us */
- while (resp->hdr.status == PFVF_STATUS_FAILURE) {
- DP(BNX2X_MSG_IOV,
- "vfpf SET MAC failed. Check bulletin board for new posts\n");
-
- /* check if bulletin board was updated */
- if (bnx2x_sample_bulletin(bp) == PFVF_BULLETIN_UPDATED) {
- /* copy mac from device to request */
- memcpy(req->filters[0].mac, bp->dev->dev_addr,
- ETH_ALEN);
-
- /* send message to pf */
- rc = bnx2x_send_msg2pf(bp, &resp->hdr.status,
- bp->vf2pf_mbox_mapping);
- } else {
- /* no new info in bulletin */
- break;
- }
- }
+ struct bnx2x *bp = fp->bp;
+ u32 offset = BAR_USTRORM_INTMEM;
- if (resp->hdr.status != PFVF_STATUS_SUCCESS) {
- BNX2X_ERR("vfpf SET MAC failed: %d\n", resp->hdr.status);
- return -EINVAL;
- }
+ if (IS_VF(bp))
+ return bnx2x_vf_ustorm_prods_offset(bp, fp);
+ else if (!CHIP_IS_E1x(bp))
+ offset += USTORM_RX_PRODS_E2_OFFSET(fp->cl_qzone_id);
+ else
+ offset += USTORM_RX_PRODS_E1X_OFFSET(BP_PORT(bp), fp->cl_id);
- return 0;
+ return offset;
}
-int bnx2x_vfpf_set_mcast(struct net_device *dev)
+/* called only on E1H or E2.
+ * When pretending to be PF, the pretend value is the function number 0...7
+ * When pretending to be VF, the pretend val is the PF-num:VF-valid:ABS-VFID
+ * combination
+ */
+int bnx2x_pretend_func(struct bnx2x *bp, u16 pretend_func_val)
{
- struct bnx2x *bp = netdev_priv(dev);
- struct vfpf_set_q_filters_tlv *req = &bp->vf2pf_mbox->req.set_q_filters;
- struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
- int rc, i = 0;
- struct netdev_hw_addr *ha;
+ u32 pretend_reg;
- if (bp->state != BNX2X_STATE_OPEN) {
- DP(NETIF_MSG_IFUP, "state is %x, returning\n", bp->state);
- return -EINVAL;
- }
-
- /* clear mailbox and prep first tlv */
- bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_SET_Q_FILTERS,
- sizeof(*req));
-
- /* Get Rx mode requested */
- DP(NETIF_MSG_IFUP, "dev->flags = %x\n", dev->flags);
-
- netdev_for_each_mc_addr(ha, dev) {
- DP(NETIF_MSG_IFUP, "Adding mcast MAC: %pM\n",
- bnx2x_mc_addr(ha));
- memcpy(req->multicast[i], bnx2x_mc_addr(ha), ETH_ALEN);
- i++;
- }
-
- /* We support four PFVF_MAX_MULTICAST_PER_VF mcast
- * addresses tops
- */
- if (i >= PFVF_MAX_MULTICAST_PER_VF) {
- DP(NETIF_MSG_IFUP,
- "VF supports not more than %d multicast MAC addresses\n",
- PFVF_MAX_MULTICAST_PER_VF);
- return -EINVAL;
- }
-
- req->n_multicast = i;
- req->flags |= VFPF_SET_Q_FILTERS_MULTICAST_CHANGED;
- req->vf_qid = 0;
-
- /* add list termination tlv */
- bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
- sizeof(struct channel_list_end_tlv));
-
- /* output tlvs list */
- bnx2x_dp_tlv_list(bp, req);
-
- rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
- if (rc) {
- BNX2X_ERR("Sending a message failed: %d\n", rc);
- return rc;
- }
-
- if (resp->hdr.status != PFVF_STATUS_SUCCESS) {
- BNX2X_ERR("Set Rx mode/multicast failed: %d\n",
- resp->hdr.status);
- return -EINVAL;
- }
+ if (CHIP_IS_E1H(bp) && pretend_func_val > E1H_FUNC_MAX)
+ return -1;
+ /* get my own pretend register */
+ pretend_reg = bnx2x_get_pretend_reg(bp);
+ REG_WR(bp, pretend_reg, pretend_func_val);
+ REG_RD(bp, pretend_reg);
return 0;
}
-
-int bnx2x_vfpf_storm_rx_mode(struct bnx2x *bp)
-{
- int mode = bp->rx_mode;
- struct vfpf_set_q_filters_tlv *req = &bp->vf2pf_mbox->req.set_q_filters;
- struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
- int rc;
-
- /* clear mailbox and prep first tlv */
- bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_SET_Q_FILTERS,
- sizeof(*req));
-
- DP(NETIF_MSG_IFUP, "Rx mode is %d\n", mode);
-
- switch (mode) {
- case BNX2X_RX_MODE_NONE: /* no Rx */
- req->rx_mask = VFPF_RX_MASK_ACCEPT_NONE;
- break;
- case BNX2X_RX_MODE_NORMAL:
- req->rx_mask = VFPF_RX_MASK_ACCEPT_MATCHED_MULTICAST;
- req->rx_mask |= VFPF_RX_MASK_ACCEPT_MATCHED_UNICAST;
- req->rx_mask |= VFPF_RX_MASK_ACCEPT_BROADCAST;
- break;
- case BNX2X_RX_MODE_ALLMULTI:
- req->rx_mask = VFPF_RX_MASK_ACCEPT_ALL_MULTICAST;
- req->rx_mask |= VFPF_RX_MASK_ACCEPT_MATCHED_UNICAST;
- req->rx_mask |= VFPF_RX_MASK_ACCEPT_BROADCAST;
- break;
- case BNX2X_RX_MODE_PROMISC:
- req->rx_mask = VFPF_RX_MASK_ACCEPT_ALL_UNICAST;
- req->rx_mask |= VFPF_RX_MASK_ACCEPT_ALL_MULTICAST;
- req->rx_mask |= VFPF_RX_MASK_ACCEPT_BROADCAST;
- break;
- default:
- BNX2X_ERR("BAD rx mode (%d)\n", mode);
- return -EINVAL;
- }
-
- req->flags |= VFPF_SET_Q_FILTERS_RX_MASK_CHANGED;
- req->vf_qid = 0;
-
- /* add list termination tlv */
- bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
- sizeof(struct channel_list_end_tlv));
-
- /* output tlvs list */
- bnx2x_dp_tlv_list(bp, req);
-
- rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
- if (rc)
- BNX2X_ERR("Sending a message failed: %d\n", rc);
-
- if (resp->hdr.status != PFVF_STATUS_SUCCESS) {
- BNX2X_ERR("Set Rx mode failed: %d\n", resp->hdr.status);
- return -EINVAL;
- }
-
- return rc;
-}
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c
index 71fcef0..f2f5c8e 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.c
@@ -20,7 +20,7 @@
#include "bnx2x.h"
#include "bnx2x_init.h"
#include "bnx2x_cmn.h"
-#include "bnx2x_sriov.h"
+#include <linux/crc32.h>
/* General service functions */
static void storm_memset_vf_to_pf(struct bnx2x *bp, u16 abs_fid,
@@ -1334,25 +1334,6 @@ int bnx2x_vfop_qdown_cmd(struct bnx2x *bp,
* for calling pretend prior to calling these routines
*/
-/* called only on E1H or E2.
- * When pretending to be PF, the pretend value is the function number 0...7
- * When pretending to be VF, the pretend val is the PF-num:VF-valid:ABS-VFID
- * combination
- */
-int bnx2x_pretend_func(struct bnx2x *bp, u16 pretend_func_val)
-{
- u32 pretend_reg;
-
- if (CHIP_IS_E1H(bp) && pretend_func_val > E1H_FUNC_MAX)
- return -1;
-
- /* get my own pretend register */
- pretend_reg = bnx2x_get_pretend_reg(bp);
- REG_WR(bp, pretend_reg, pretend_func_val);
- REG_RD(bp, pretend_reg);
- return 0;
-}
-
/* internal vf enable - until vf is enabled internally all transactions
* are blocked. this routine should always be called last with pretend.
*/
@@ -1800,7 +1781,7 @@ static void bnx2x_vf_set_bars(struct bnx2x *bp, struct bnx2x_virtf *vf)
u64 start = pci_resource_start(dev, PCI_IOV_RESOURCES + i);
u32 size = pci_resource_len(dev, PCI_IOV_RESOURCES + i);
- do_div(size, iov->total);
+ size /= iov->total;
vf->bars[n].bar = start + size * vf->abs_vfid;
vf->bars[n].size = size;
}
@@ -3031,3 +3012,188 @@ void bnx2x_unlock_vf_pf_channel(struct bnx2x *bp, struct bnx2x_virtf *vf,
/* record the locking op */
vf->op_current = CHANNEL_TLV_NONE;
}
+
+void bnx2x_enable_sriov(struct bnx2x *bp)
+{
+ int rc = 0;
+
+ /* disbale sriov in case it is still enabled */
+ pci_disable_sriov(bp->pdev);
+ DP(BNX2X_MSG_IOV, "sriov disabled\n");
+
+ /* enable sriov */
+ DP(BNX2X_MSG_IOV, "vf num (%d)\n", (bp->vfdb->sriov.nr_virtfn));
+ rc = pci_enable_sriov(bp->pdev, (bp->vfdb->sriov.nr_virtfn));
+ if (rc)
+ BNX2X_ERR("pci_enable_sriov failed with %d\n", rc);
+ else
+ DP(BNX2X_MSG_IOV, "sriov enabled\n");
+}
+
+/* New mac for VF. Consider these cases:
+ * 1. VF hasn't been acquired yet - save the mac in local bulletin board and
+ * supply at acquire.
+ * 2. VF has already been acquired but has not yet initialized - store in local
+ * bulletin board. mac will be posted on VF bulletin board after VF init. VF
+ * will configure this mac when it is ready.
+ * 3. VF has already initialized but has not yet setup a queue - post the new
+ * mac on VF's bulletin board right now. VF will configure this mac when it
+ * is ready.
+ * 4. VF has already set a queue - delete any macs already configured for this
+ * queue and manually config the new mac.
+ * In any event, once this function has been called refuse any attempts by the
+ * VF to configure any mac for itself except for this mac. In case of a race
+ * where the VF fails to see the new post on its bulletin board before sending a
+ * mac configuration request, the PF will simply fail the request and VF can try
+ * again after consulting its bulletin board
+ */
+int bnx2x_set_vf_mac(struct net_device *dev, int queue, u8 *mac)
+{
+ struct bnx2x *bp = netdev_priv(dev);
+ int rc, q_logical_state, vfidx = queue;
+ struct bnx2x_virtf *vf = BP_VF(bp, vfidx);
+ struct pf_vf_bulletin_content *bulletin = BP_VF_BULLETIN(bp, vfidx);
+
+ /* if SRIOV is disabled there is nothing to do (and somewhere, someone
+ * has erred).
+ */
+ if (!IS_SRIOV(bp)) {
+ BNX2X_ERR("bnx2x_set_vf_mac called though sriov is disabled\n");
+ return -EINVAL;
+ }
+
+ if (!is_valid_ether_addr(mac)) {
+ BNX2X_ERR("mac address invalid\n");
+ return -EINVAL;
+ }
+
+ /* update PF's copy of the VF's bulletin. will no longer accept mac
+ * configuration requests from vf unless match this mac
+ */
+ bulletin->valid_bitmap |= 1 << MAC_ADDR_VALID;
+ memcpy(bulletin->mac, mac, ETH_ALEN);
+
+ /* Post update on VF's bulletin board */
+ rc = bnx2x_post_vf_bulletin(bp, vfidx);
+ if (rc) {
+ BNX2X_ERR("failed to update VF[%d] bulletin\n", vfidx);
+ return rc;
+ }
+
+ /* is vf initialized and queue set up? */
+ q_logical_state =
+ bnx2x_get_q_logical_state(bp, &bnx2x_vfq(vf, 0, sp_obj));
+ if (vf->state == VF_ENABLED &&
+ q_logical_state == BNX2X_Q_LOGICAL_STATE_ACTIVE) {
+ /* configure the mac in device on this vf's queue */
+ unsigned long flags = 0;
+ struct bnx2x_vlan_mac_obj *mac_obj = &bnx2x_vfq(vf, 0, mac_obj);
+
+ /* must lock vfpf channel to protect against vf flows */
+ bnx2x_lock_vf_pf_channel(bp, vf, CHANNEL_TLV_PF_SET_MAC);
+
+ /* remove existing eth macs */
+ rc = bnx2x_del_all_macs(bp, mac_obj, BNX2X_ETH_MAC, true);
+ if (rc) {
+ BNX2X_ERR("failed to delete eth macs\n");
+ return -EINVAL;
+ }
+
+ /* remove existing uc list macs */
+ rc = bnx2x_del_all_macs(bp, mac_obj, BNX2X_UC_LIST_MAC, true);
+ if (rc) {
+ BNX2X_ERR("failed to delete uc_list macs\n");
+ return -EINVAL;
+ }
+
+ /* configure the new mac to device */
+ __set_bit(RAMROD_COMP_WAIT, &flags);
+ bnx2x_set_mac_one(bp, (u8 *)&bulletin->mac, mac_obj, true,
+ BNX2X_ETH_MAC, &flags);
+
+ bnx2x_unlock_vf_pf_channel(bp, vf, CHANNEL_TLV_PF_SET_MAC);
+ }
+
+ return rc;
+}
+
+/* crc is the first field in the bulletin board. compute the crc over the
+ * entire bulletin board excluding the crc field itself
+ */
+u32 bnx2x_crc_vf_bulletin(struct bnx2x *bp,
+ struct pf_vf_bulletin_content *bulletin)
+{
+ return crc32(BULLETIN_CRC_SEED,
+ ((u8 *)bulletin) + sizeof(bulletin->crc),
+ BULLETIN_CONTENT_SIZE - sizeof(bulletin->crc));
+}
+
+/* Check for new posts on the bulletin board */
+enum sample_bulletin_result bnx2x_sample_bulletin(struct bnx2x *bp)
+{
+ struct pf_vf_bulletin_content bulletin = bp->pf2vf_bulletin->content;
+ int attempts;
+
+ /* bulletin board hasn't changed since last sample */
+ if (bp->old_bulletin.version == bulletin.version)
+ return PFVF_BULLETIN_UNCHANGED;
+
+ /* validate crc of new bulletin board */
+ if (bp->old_bulletin.version != bp->pf2vf_bulletin->content.version) {
+ /* sampling structure in mid post may result with corrupted data
+ * validate crc to ensure coherency.
+ */
+ for (attempts = 0; attempts < BULLETIN_ATTEMPTS; attempts++) {
+ bulletin = bp->pf2vf_bulletin->content;
+ if (bulletin.crc == bnx2x_crc_vf_bulletin(bp,
+ &bulletin))
+ break;
+ BNX2X_ERR("bad crc on bulletin board. contained %x computed %x\n",
+ bulletin.crc,
+ bnx2x_crc_vf_bulletin(bp, &bulletin));
+ }
+ if (attempts >= BULLETIN_ATTEMPTS) {
+ BNX2X_ERR("pf to vf bulletin board crc was wrong %d consecutive times. Aborting\n",
+ attempts);
+ return PFVF_BULLETIN_CRC_ERR;
+ }
+ }
+
+ /* the mac address in bulletin board is valid and is new */
+ if (bulletin.valid_bitmap & 1 << MAC_ADDR_VALID &&
+ memcmp(bulletin.mac, bp->old_bulletin.mac, ETH_ALEN)) {
+ /* update new mac to net device */
+ memcpy(bp->dev->dev_addr, bulletin.mac, ETH_ALEN);
+ }
+
+ /* copy new bulletin board to bp */
+ bp->old_bulletin = bulletin;
+
+ return PFVF_BULLETIN_UPDATED;
+}
+
+void bnx2x_vf_map_doorbells(struct bnx2x *bp)
+{
+ /* vf doorbells are embedded within the regview */
+ bp->doorbells = bp->regview + PXP_VF_ADDR_DB_START;
+}
+
+int bnx2x_vf_pci_alloc(struct bnx2x *bp)
+{
+ /* allocate vf2pf mailbox for vf to pf channel */
+ BNX2X_PCI_ALLOC(bp->vf2pf_mbox, &bp->vf2pf_mbox_mapping,
+ sizeof(struct bnx2x_vf_mbx_msg));
+
+ /* allocate pf 2 vf bulletin board */
+ BNX2X_PCI_ALLOC(bp->pf2vf_bulletin, &bp->pf2vf_bulletin_mapping,
+ sizeof(union pf_vf_bulletin));
+
+ return 0;
+
+alloc_mem_err:
+ BNX2X_PCI_FREE(bp->vf2pf_mbox, bp->vf2pf_mbox_mapping,
+ sizeof(struct bnx2x_vf_mbx_msg));
+ BNX2X_PCI_FREE(bp->vf2pf_mbox, bp->vf2pf_mbox_mapping,
+ sizeof(union pf_vf_bulletin));
+ return -ENOMEM;
+}
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.h b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.h
index aab2a05..df4ae74 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.h
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_sriov.h
@@ -20,7 +20,15 @@
#define BNX2X_SRIOV_H
#include "bnx2x_vfpf.h"
-#include "bnx2x_cmn.h"
+#include "bnx2x.h"
+
+enum sample_bulletin_result {
+ PFVF_BULLETIN_UNCHANGED,
+ PFVF_BULLETIN_UPDATED,
+ PFVF_BULLETIN_CRC_ERR
+};
+
+#ifdef CONFIG_BNX2X_SRIOV
/* The bnx2x device structure holds vfdb structure described below.
* The VF array is indexed by the relative vfid.
@@ -712,12 +720,89 @@ u32 bnx2x_crc_vf_bulletin(struct bnx2x *bp,
struct pf_vf_bulletin_content *bulletin);
int bnx2x_post_vf_bulletin(struct bnx2x *bp, int vf);
-enum sample_bulletin_result {
- PFVF_BULLETIN_UNCHANGED,
- PFVF_BULLETIN_UPDATED,
- PFVF_BULLETIN_CRC_ERR
-};
enum sample_bulletin_result bnx2x_sample_bulletin(struct bnx2x *bp);
+/* VF side vfpf channel functions */
+int bnx2x_vfpf_acquire(struct bnx2x *bp, u8 tx_count, u8 rx_count);
+int bnx2x_vfpf_release(struct bnx2x *bp);
+int bnx2x_vfpf_release(struct bnx2x *bp);
+int bnx2x_vfpf_init(struct bnx2x *bp);
+void bnx2x_vfpf_close_vf(struct bnx2x *bp);
+int bnx2x_vfpf_setup_q(struct bnx2x *bp, int fp_idx);
+int bnx2x_vfpf_teardown_queue(struct bnx2x *bp, int qidx);
+int bnx2x_vfpf_set_mac(struct bnx2x *bp);
+int bnx2x_vfpf_set_mcast(struct net_device *dev);
+int bnx2x_vfpf_storm_rx_mode(struct bnx2x *bp);
+
+static inline void bnx2x_vf_fill_fw_str(struct bnx2x *bp, char *buf,
+ size_t buf_len)
+{
+ strlcpy(buf, bp->acquire_resp.pfdev_info.fw_ver, buf_len);
+}
+
+static inline int bnx2x_vf_ustorm_prods_offset(struct bnx2x *bp,
+ struct bnx2x_fastpath *fp)
+{
+ return PXP_VF_ADDR_USDM_QUEUES_START +
+ bp->acquire_resp.resc.hw_qid[fp->index] *
+ sizeof(struct ustorm_queue_zone_data);
+}
+
+enum sample_bulletin_result bnx2x_sample_bulletin(struct bnx2x *bp);
+void bnx2x_vf_map_doorbells(struct bnx2x *bp);
+int bnx2x_vf_pci_alloc(struct bnx2x *bp);
+void bnx2x_enable_sriov(struct bnx2x *bp);
+static inline int bnx2x_vf_headroom(struct bnx2x *bp)
+{
+ return bp->vfdb->sriov.nr_virtfn * BNX2X_CLIENTS_PER_VF;
+}
+
+#else /* CONFIG_BNX2X_SRIOV */
+
+static inline void bnx2x_iov_set_queue_sp_obj(struct bnx2x *bp, int vf_cid,
+ struct bnx2x_queue_sp_obj **q_obj) {}
+static inline void bnx2x_iov_sp_event(struct bnx2x *bp, int vf_cid,
+ bool queue_work) {}
+static inline void bnx2x_vf_handle_flr_event(struct bnx2x *bp) {}
+static inline int bnx2x_iov_eq_sp_event(struct bnx2x *bp,
+ union event_ring_elem *elem) {return 1; }
+static inline void bnx2x_iov_sp_task(struct bnx2x *bp) {}
+static inline void bnx2x_vf_mbx(struct bnx2x *bp,
+ struct vf_pf_event_data *vfpf_event) {}
+static inline int bnx2x_iov_init_ilt(struct bnx2x *bp, u16 line) {return line; }
+static inline void bnx2x_iov_init_dq(struct bnx2x *bp) {}
+static inline int bnx2x_iov_alloc_mem(struct bnx2x *bp) {return 0; }
+static inline int bnx2x_iov_chip_cleanup(struct bnx2x *bp) {return 0; }
+static inline void bnx2x_iov_init_dmae(struct bnx2x *bp) {}
+static inline int bnx2x_iov_init_one(struct bnx2x *bp, int int_mode_param,
+ int num_vfs_param) {return 0; }
+static inline void bnx2x_iov_remove_one(struct bnx2x *bp) {}
+static inline void bnx2x_enable_sriov(struct bnx2x *bp) {}
+static inline int bnx2x_vfpf_acquire(struct bnx2x *bp,
+ u8 tx_count, u8 rx_count) {return 0; }
+static inline int bnx2x_vfpf_release(struct bnx2x *bp) {return 0; }
+static inline int bnx2x_vfpf_init(struct bnx2x *bp) {return 0; }
+static inline void bnx2x_vfpf_close_vf(struct bnx2x *bp) {}
+static inline int bnx2x_vfpf_setup_q(struct bnx2x *bp, int fp_idx) {return 0; }
+static inline int bnx2x_vfpf_teardown_queue(struct bnx2x *bp, int qidx) {return 0; }
+static inline int bnx2x_vfpf_set_mac(struct bnx2x *bp) {return 0; }
+static inline int bnx2x_vfpf_set_mcast(struct net_device *dev) {return 0; }
+static inline int bnx2x_vfpf_storm_rx_mode(struct bnx2x *bp) {return 0; }
+static inline int bnx2x_iov_nic_init(struct bnx2x *bp) {return 0; }
+static inline int bnx2x_vf_headroom(struct bnx2x *bp) {return 0; }
+static inline void bnx2x_iov_adjust_stats_req(struct bnx2x *bp) {}
+static inline void bnx2x_vf_fill_fw_str(struct bnx2x *bp, char *buf,
+ size_t buf_len) {}
+static inline int bnx2x_vf_ustorm_prods_offset(struct bnx2x *bp,
+ struct bnx2x_fastpath *fp) {return 0; }
+static inline enum sample_bulletin_result bnx2x_sample_bulletin(struct bnx2x *bp)
+{
+ return PFVF_BULLETIN_UNCHANGED;
+}
+
+static inline int bnx2x_vf_map_doorbells(struct bnx2x *bp) {return 0; }
+static inline int bnx2x_vf_pci_alloc(struct bnx2x *bp) {return 0; }
+
+#endif /* CONFIG_BNX2X_SRIOV */
#endif /* bnx2x_sriov.h */
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.c b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.c
index b410b9f..850aad3 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.c
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.c
@@ -18,7 +18,7 @@
*/
#include "bnx2x.h"
-#include "bnx2x_sriov.h"
+#include "bnx2x_cmn.h"
#include <linux/crc32.h>
/* place a given tlv on the tlv buffer at a given offset */
@@ -98,6 +98,622 @@ static inline int bnx2x_pfvf_status_codes(int rc)
}
}
+int bnx2x_send_msg2pf(struct bnx2x *bp, u8 *done, dma_addr_t msg_mapping)
+{
+ struct cstorm_vf_zone_data __iomem *zone_data =
+ REG_ADDR(bp, PXP_VF_ADDR_CSDM_GLOBAL_START);
+ int tout = 600, interval = 100; /* wait for 60 seconds */
+
+ if (*done) {
+ BNX2X_ERR("done was non zero before message to pf was sent\n");
+ WARN_ON(true);
+ return -EINVAL;
+ }
+
+ /* Write message address */
+ writel(U64_LO(msg_mapping),
+ &zone_data->non_trigger.vf_pf_channel.msg_addr_lo);
+ writel(U64_HI(msg_mapping),
+ &zone_data->non_trigger.vf_pf_channel.msg_addr_hi);
+
+ /* make sure the address is written before FW accesses it */
+ wmb();
+
+ /* Trigger the PF FW */
+ writeb(1, &zone_data->trigger.vf_pf_channel.addr_valid);
+
+ /* Wait for PF to complete */
+ while ((tout >= 0) && (!*done)) {
+ msleep(interval);
+ tout -= 1;
+
+ /* progress indicator - HV can take its own sweet time in
+ * answering VFs...
+ */
+ DP_CONT(BNX2X_MSG_IOV, ".");
+ }
+
+ if (!*done) {
+ BNX2X_ERR("PF response has timed out\n");
+ return -EAGAIN;
+ }
+ DP(BNX2X_MSG_SP, "Got a response from PF\n");
+ return 0;
+}
+
+int bnx2x_get_vf_id(struct bnx2x *bp, u32 *vf_id)
+{
+ u32 me_reg;
+ int tout = 10, interval = 100; /* Wait for 1 sec */
+
+ do {
+ /* pxp traps vf read of doorbells and returns me reg value */
+ me_reg = readl(bp->doorbells);
+ if (GOOD_ME_REG(me_reg))
+ break;
+
+ msleep(interval);
+
+ BNX2X_ERR("Invalid ME register value: 0x%08x\n. Is pf driver up?",
+ me_reg);
+ } while (tout-- > 0);
+
+ if (!GOOD_ME_REG(me_reg)) {
+ BNX2X_ERR("Invalid ME register value: 0x%08x\n", me_reg);
+ return -EINVAL;
+ }
+
+ BNX2X_ERR("valid ME register value: 0x%08x\n", me_reg);
+
+ *vf_id = (me_reg & ME_REG_VF_NUM_MASK) >> ME_REG_VF_NUM_SHIFT;
+
+ return 0;
+}
+
+int bnx2x_vfpf_acquire(struct bnx2x *bp, u8 tx_count, u8 rx_count)
+{
+ int rc = 0, attempts = 0;
+ struct vfpf_acquire_tlv *req = &bp->vf2pf_mbox->req.acquire;
+ struct pfvf_acquire_resp_tlv *resp = &bp->vf2pf_mbox->resp.acquire_resp;
+ u32 vf_id;
+ bool resources_acquired = false;
+
+ /* clear mailbox and prep first tlv */
+ bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_ACQUIRE, sizeof(*req));
+
+ if (bnx2x_get_vf_id(bp, &vf_id))
+ return -EAGAIN;
+
+ req->vfdev_info.vf_id = vf_id;
+ req->vfdev_info.vf_os = 0;
+
+ req->resc_request.num_rxqs = rx_count;
+ req->resc_request.num_txqs = tx_count;
+ req->resc_request.num_sbs = bp->igu_sb_cnt;
+ req->resc_request.num_mac_filters = VF_ACQUIRE_MAC_FILTERS;
+ req->resc_request.num_mc_filters = VF_ACQUIRE_MC_FILTERS;
+
+ /* pf 2 vf bulletin board address */
+ req->bulletin_addr = bp->pf2vf_bulletin_mapping;
+
+ /* add list termination tlv */
+ bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
+ sizeof(struct channel_list_end_tlv));
+
+ /* output tlvs list */
+ bnx2x_dp_tlv_list(bp, req);
+
+ while (!resources_acquired) {
+ DP(BNX2X_MSG_SP, "attempting to acquire resources\n");
+
+ /* send acquire request */
+ rc = bnx2x_send_msg2pf(bp,
+ &resp->hdr.status,
+ bp->vf2pf_mbox_mapping);
+
+ /* PF timeout */
+ if (rc)
+ return rc;
+
+ /* copy acquire response from buffer to bp */
+ memcpy(&bp->acquire_resp, resp, sizeof(bp->acquire_resp));
+
+ attempts++;
+
+ /* test whether the PF accepted our request. If not, humble the
+ * the request and try again.
+ */
+ if (bp->acquire_resp.hdr.status == PFVF_STATUS_SUCCESS) {
+ DP(BNX2X_MSG_SP, "resources acquired\n");
+ resources_acquired = true;
+ } else if (bp->acquire_resp.hdr.status ==
+ PFVF_STATUS_NO_RESOURCE &&
+ attempts < VF_ACQUIRE_THRESH) {
+ DP(BNX2X_MSG_SP,
+ "PF unwilling to fulfill resource request. Try PF recommended amount\n");
+
+ /* humble our request */
+ req->resc_request.num_txqs =
+ bp->acquire_resp.resc.num_txqs;
+ req->resc_request.num_rxqs =
+ bp->acquire_resp.resc.num_rxqs;
+ req->resc_request.num_sbs =
+ bp->acquire_resp.resc.num_sbs;
+ req->resc_request.num_mac_filters =
+ bp->acquire_resp.resc.num_mac_filters;
+ req->resc_request.num_vlan_filters =
+ bp->acquire_resp.resc.num_vlan_filters;
+ req->resc_request.num_mc_filters =
+ bp->acquire_resp.resc.num_mc_filters;
+
+ /* Clear response buffer */
+ memset(&bp->vf2pf_mbox->resp, 0,
+ sizeof(union pfvf_tlvs));
+ } else {
+ /* PF reports error */
+ BNX2X_ERR("Failed to get the requested amount of resources: %d. Breaking...\n",
+ bp->acquire_resp.hdr.status);
+ return -EAGAIN;
+ }
+ }
+
+ /* get HW info */
+ bp->common.chip_id |= (bp->acquire_resp.pfdev_info.chip_num & 0xffff);
+ bp->link_params.chip_id = bp->common.chip_id;
+ bp->db_size = bp->acquire_resp.pfdev_info.db_size;
+ bp->common.int_block = INT_BLOCK_IGU;
+ bp->common.chip_port_mode = CHIP_2_PORT_MODE;
+ bp->igu_dsb_id = -1;
+ bp->mf_ov = 0;
+ bp->mf_mode = 0;
+ bp->common.flash_size = 0;
+ bp->flags |=
+ NO_WOL_FLAG | NO_ISCSI_OOO_FLAG | NO_ISCSI_FLAG | NO_FCOE_FLAG;
+ bp->igu_sb_cnt = 1;
+ bp->igu_base_sb = bp->acquire_resp.resc.hw_sbs[0].hw_sb_id;
+ strlcpy(bp->fw_ver, bp->acquire_resp.pfdev_info.fw_ver,
+ sizeof(bp->fw_ver));
+
+ if (is_valid_ether_addr(bp->acquire_resp.resc.current_mac_addr))
+ memcpy(bp->dev->dev_addr,
+ bp->acquire_resp.resc.current_mac_addr,
+ ETH_ALEN);
+
+ return 0;
+}
+
+int bnx2x_vfpf_release(struct bnx2x *bp)
+{
+ struct vfpf_release_tlv *req = &bp->vf2pf_mbox->req.release;
+ struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
+ u32 rc = 0, vf_id;
+
+ /* clear mailbox and prep first tlv */
+ bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_RELEASE, sizeof(*req));
+
+ if (bnx2x_get_vf_id(bp, &vf_id))
+ return -EAGAIN;
+
+ req->vf_id = vf_id;
+
+ /* add list termination tlv */
+ bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
+ sizeof(struct channel_list_end_tlv));
+
+ /* output tlvs list */
+ bnx2x_dp_tlv_list(bp, req);
+
+ /* send release request */
+ rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
+
+ if (rc)
+ /* PF timeout */
+ return rc;
+ if (resp->hdr.status == PFVF_STATUS_SUCCESS) {
+ /* PF released us */
+ DP(BNX2X_MSG_SP, "vf released\n");
+ } else {
+ /* PF reports error */
+ BNX2X_ERR("PF failed our release request - are we out of sync? response status: %d\n",
+ resp->hdr.status);
+ return -EAGAIN;
+ }
+
+ return 0;
+}
+
+/* Tell PF about SB addresses */
+int bnx2x_vfpf_init(struct bnx2x *bp)
+{
+ struct vfpf_init_tlv *req = &bp->vf2pf_mbox->req.init;
+ struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
+ int rc, i;
+
+ /* clear mailbox and prep first tlv */
+ bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_INIT, sizeof(*req));
+
+ /* status blocks */
+ for_each_eth_queue(bp, i)
+ req->sb_addr[i] = (dma_addr_t)bnx2x_fp(bp, i,
+ status_blk_mapping);
+
+ /* statistics - requests only supports single queue for now */
+ req->stats_addr = bp->fw_stats_data_mapping +
+ offsetof(struct bnx2x_fw_stats_data, queue_stats);
+
+ /* add list termination tlv */
+ bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
+ sizeof(struct channel_list_end_tlv));
+
+ /* output tlvs list */
+ bnx2x_dp_tlv_list(bp, req);
+
+ rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
+ if (rc)
+ return rc;
+
+ if (resp->hdr.status != PFVF_STATUS_SUCCESS) {
+ BNX2X_ERR("INIT VF failed: %d. Breaking...\n",
+ resp->hdr.status);
+ return -EAGAIN;
+ }
+
+ DP(BNX2X_MSG_SP, "INIT VF Succeeded\n");
+ return 0;
+}
+
+/* CLOSE VF - opposite to INIT_VF */
+void bnx2x_vfpf_close_vf(struct bnx2x *bp)
+{
+ struct vfpf_close_tlv *req = &bp->vf2pf_mbox->req.close;
+ struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
+ int i, rc;
+ u32 vf_id;
+
+ /* If we haven't got a valid VF id, there is no sense to
+ * continue with sending messages
+ */
+ if (bnx2x_get_vf_id(bp, &vf_id))
+ goto free_irq;
+
+ /* Close the queues */
+ for_each_queue(bp, i)
+ bnx2x_vfpf_teardown_queue(bp, i);
+
+ /* clear mailbox and prep first tlv */
+ bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_CLOSE, sizeof(*req));
+
+ req->vf_id = vf_id;
+
+ /* add list termination tlv */
+ bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
+ sizeof(struct channel_list_end_tlv));
+
+ /* output tlvs list */
+ bnx2x_dp_tlv_list(bp, req);
+
+ rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
+
+ if (rc)
+ BNX2X_ERR("Sending CLOSE failed. rc was: %d\n", rc);
+
+ else if (resp->hdr.status != PFVF_STATUS_SUCCESS)
+ BNX2X_ERR("Sending CLOSE failed: pf response was %d\n",
+ resp->hdr.status);
+
+free_irq:
+ /* Disable HW interrupts, NAPI */
+ bnx2x_netif_stop(bp, 0);
+ /* Delete all NAPI objects */
+ bnx2x_del_all_napi(bp);
+
+ /* Release IRQs */
+ bnx2x_free_irq(bp);
+}
+
+/* ask the pf to open a queue for the vf */
+int bnx2x_vfpf_setup_q(struct bnx2x *bp, int fp_idx)
+{
+ struct vfpf_setup_q_tlv *req = &bp->vf2pf_mbox->req.setup_q;
+ struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
+ struct bnx2x_fastpath *fp = &bp->fp[fp_idx];
+ u16 tpa_agg_size = 0, flags = 0;
+ int rc;
+
+ /* clear mailbox and prep first tlv */
+ bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_SETUP_Q, sizeof(*req));
+
+ /* select tpa mode to request */
+ if (!fp->disable_tpa) {
+ flags |= VFPF_QUEUE_FLG_TPA;
+ flags |= VFPF_QUEUE_FLG_TPA_IPV6;
+ if (fp->mode == TPA_MODE_GRO)
+ flags |= VFPF_QUEUE_FLG_TPA_GRO;
+ tpa_agg_size = TPA_AGG_SIZE;
+ }
+
+ /* calculate queue flags */
+ flags |= VFPF_QUEUE_FLG_STATS;
+ flags |= VFPF_QUEUE_FLG_CACHE_ALIGN;
+ flags |= IS_MF_SD(bp) ? VFPF_QUEUE_FLG_OV : 0;
+ flags |= VFPF_QUEUE_FLG_VLAN;
+ DP(NETIF_MSG_IFUP, "vlan removal enabled\n");
+
+ /* Common */
+ req->vf_qid = fp_idx;
+ req->param_valid = VFPF_RXQ_VALID | VFPF_TXQ_VALID;
+
+ /* Rx */
+ req->rxq.rcq_addr = fp->rx_comp_mapping;
+ req->rxq.rcq_np_addr = fp->rx_comp_mapping + BCM_PAGE_SIZE;
+ req->rxq.rxq_addr = fp->rx_desc_mapping;
+ req->rxq.sge_addr = fp->rx_sge_mapping;
+ req->rxq.vf_sb = fp_idx;
+ req->rxq.sb_index = HC_INDEX_ETH_RX_CQ_CONS;
+ req->rxq.hc_rate = bp->rx_ticks ? 1000000/bp->rx_ticks : 0;
+ req->rxq.mtu = bp->dev->mtu;
+ req->rxq.buf_sz = fp->rx_buf_size;
+ req->rxq.sge_buf_sz = BCM_PAGE_SIZE * PAGES_PER_SGE;
+ req->rxq.tpa_agg_sz = tpa_agg_size;
+ req->rxq.max_sge_pkt = SGE_PAGE_ALIGN(bp->dev->mtu) >> SGE_PAGE_SHIFT;
+ req->rxq.max_sge_pkt = ((req->rxq.max_sge_pkt + PAGES_PER_SGE - 1) &
+ (~(PAGES_PER_SGE-1))) >> PAGES_PER_SGE_SHIFT;
+ req->rxq.flags = flags;
+ req->rxq.drop_flags = 0;
+ req->rxq.cache_line_log = BNX2X_RX_ALIGN_SHIFT;
+ req->rxq.stat_id = -1; /* No stats at the moment */
+
+ /* Tx */
+ req->txq.txq_addr = fp->txdata_ptr[FIRST_TX_COS_INDEX]->tx_desc_mapping;
+ req->txq.vf_sb = fp_idx;
+ req->txq.sb_index = HC_INDEX_ETH_TX_CQ_CONS_COS0;
+ req->txq.hc_rate = bp->tx_ticks ? 1000000/bp->tx_ticks : 0;
+ req->txq.flags = flags;
+ req->txq.traffic_type = LLFC_TRAFFIC_TYPE_NW;
+
+ /* add list termination tlv */
+ bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
+ sizeof(struct channel_list_end_tlv));
+
+ /* output tlvs list */
+ bnx2x_dp_tlv_list(bp, req);
+
+ rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
+ if (rc)
+ BNX2X_ERR("Sending SETUP_Q message for queue[%d] failed!\n",
+ fp_idx);
+
+ if (resp->hdr.status != PFVF_STATUS_SUCCESS) {
+ BNX2X_ERR("Status of SETUP_Q for queue[%d] is %d\n",
+ fp_idx, resp->hdr.status);
+ return -EINVAL;
+ }
+ return rc;
+}
+
+int bnx2x_vfpf_teardown_queue(struct bnx2x *bp, int qidx)
+{
+ struct vfpf_q_op_tlv *req = &bp->vf2pf_mbox->req.q_op;
+ struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
+ int rc;
+
+ /* clear mailbox and prep first tlv */
+ bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_TEARDOWN_Q,
+ sizeof(*req));
+
+ req->vf_qid = qidx;
+
+ /* add list termination tlv */
+ bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
+ sizeof(struct channel_list_end_tlv));
+
+ /* output tlvs list */
+ bnx2x_dp_tlv_list(bp, req);
+
+ rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
+
+ if (rc) {
+ BNX2X_ERR("Sending TEARDOWN for queue %d failed: %d\n", qidx,
+ rc);
+ return rc;
+ }
+
+ /* PF failed the transaction */
+ if (resp->hdr.status != PFVF_STATUS_SUCCESS) {
+ BNX2X_ERR("TEARDOWN for queue %d failed: %d\n", qidx,
+ resp->hdr.status);
+ return -EINVAL;
+ }
+
+ return 0;
+}
+
+/* request pf to add a mac for the vf */
+int bnx2x_vfpf_set_mac(struct bnx2x *bp)
+{
+ struct vfpf_set_q_filters_tlv *req = &bp->vf2pf_mbox->req.set_q_filters;
+ struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
+ int rc;
+
+ /* clear mailbox and prep first tlv */
+ bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_SET_Q_FILTERS,
+ sizeof(*req));
+
+ req->flags = VFPF_SET_Q_FILTERS_MAC_VLAN_CHANGED;
+ req->vf_qid = 0;
+ req->n_mac_vlan_filters = 1;
+ req->filters[0].flags =
+ VFPF_Q_FILTER_DEST_MAC_VALID | VFPF_Q_FILTER_SET_MAC;
+
+ /* sample bulletin board for new mac */
+ bnx2x_sample_bulletin(bp);
+
+ /* copy mac from device to request */
+ memcpy(req->filters[0].mac, bp->dev->dev_addr, ETH_ALEN);
+
+ /* add list termination tlv */
+ bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
+ sizeof(struct channel_list_end_tlv));
+
+ /* output tlvs list */
+ bnx2x_dp_tlv_list(bp, req);
+
+ /* send message to pf */
+ rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
+ if (rc) {
+ BNX2X_ERR("failed to send message to pf. rc was %d\n", rc);
+ return rc;
+ }
+
+ /* failure may mean PF was configured with a new mac for us */
+ while (resp->hdr.status == PFVF_STATUS_FAILURE) {
+ DP(BNX2X_MSG_IOV,
+ "vfpf SET MAC failed. Check bulletin board for new posts\n");
+
+ /* check if bulletin board was updated */
+ if (bnx2x_sample_bulletin(bp) == PFVF_BULLETIN_UPDATED) {
+ /* copy mac from device to request */
+ memcpy(req->filters[0].mac, bp->dev->dev_addr,
+ ETH_ALEN);
+
+ /* send message to pf */
+ rc = bnx2x_send_msg2pf(bp, &resp->hdr.status,
+ bp->vf2pf_mbox_mapping);
+ } else {
+ /* no new info in bulletin */
+ break;
+ }
+ }
+
+ if (resp->hdr.status != PFVF_STATUS_SUCCESS) {
+ BNX2X_ERR("vfpf SET MAC failed: %d\n", resp->hdr.status);
+ return -EINVAL;
+ }
+
+ return 0;
+}
+
+int bnx2x_vfpf_set_mcast(struct net_device *dev)
+{
+ struct bnx2x *bp = netdev_priv(dev);
+ struct vfpf_set_q_filters_tlv *req = &bp->vf2pf_mbox->req.set_q_filters;
+ struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
+ int rc, i = 0;
+ struct netdev_hw_addr *ha;
+
+ if (bp->state != BNX2X_STATE_OPEN) {
+ DP(NETIF_MSG_IFUP, "state is %x, returning\n", bp->state);
+ return -EINVAL;
+ }
+
+ /* clear mailbox and prep first tlv */
+ bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_SET_Q_FILTERS,
+ sizeof(*req));
+
+ /* Get Rx mode requested */
+ DP(NETIF_MSG_IFUP, "dev->flags = %x\n", dev->flags);
+
+ netdev_for_each_mc_addr(ha, dev) {
+ DP(NETIF_MSG_IFUP, "Adding mcast MAC: %pM\n",
+ bnx2x_mc_addr(ha));
+ memcpy(req->multicast[i], bnx2x_mc_addr(ha), ETH_ALEN);
+ i++;
+ }
+
+ /* We support four PFVF_MAX_MULTICAST_PER_VF mcast
+ * addresses tops
+ */
+ if (i >= PFVF_MAX_MULTICAST_PER_VF) {
+ DP(NETIF_MSG_IFUP,
+ "VF supports not more than %d multicast MAC addresses\n",
+ PFVF_MAX_MULTICAST_PER_VF);
+ return -EINVAL;
+ }
+
+ req->n_multicast = i;
+ req->flags |= VFPF_SET_Q_FILTERS_MULTICAST_CHANGED;
+ req->vf_qid = 0;
+
+ /* add list termination tlv */
+ bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
+ sizeof(struct channel_list_end_tlv));
+
+ /* output tlvs list */
+ bnx2x_dp_tlv_list(bp, req);
+ rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
+ if (rc) {
+ BNX2X_ERR("Sending a message failed: %d\n", rc);
+ return rc;
+ }
+
+ if (resp->hdr.status != PFVF_STATUS_SUCCESS) {
+ BNX2X_ERR("Set Rx mode/multicast failed: %d\n",
+ resp->hdr.status);
+ return -EINVAL;
+ }
+
+ return 0;
+}
+
+int bnx2x_vfpf_storm_rx_mode(struct bnx2x *bp)
+{
+ int mode = bp->rx_mode;
+ struct vfpf_set_q_filters_tlv *req = &bp->vf2pf_mbox->req.set_q_filters;
+ struct pfvf_general_resp_tlv *resp = &bp->vf2pf_mbox->resp.general_resp;
+ int rc;
+
+ /* clear mailbox and prep first tlv */
+ bnx2x_vfpf_prep(bp, &req->first_tlv, CHANNEL_TLV_SET_Q_FILTERS,
+ sizeof(*req));
+
+ DP(NETIF_MSG_IFUP, "Rx mode is %d\n", mode);
+
+ switch (mode) {
+ case BNX2X_RX_MODE_NONE: /* no Rx */
+ req->rx_mask = VFPF_RX_MASK_ACCEPT_NONE;
+ break;
+ case BNX2X_RX_MODE_NORMAL:
+ req->rx_mask = VFPF_RX_MASK_ACCEPT_MATCHED_MULTICAST;
+ req->rx_mask |= VFPF_RX_MASK_ACCEPT_MATCHED_UNICAST;
+ req->rx_mask |= VFPF_RX_MASK_ACCEPT_BROADCAST;
+ break;
+ case BNX2X_RX_MODE_ALLMULTI:
+ req->rx_mask = VFPF_RX_MASK_ACCEPT_ALL_MULTICAST;
+ req->rx_mask |= VFPF_RX_MASK_ACCEPT_MATCHED_UNICAST;
+ req->rx_mask |= VFPF_RX_MASK_ACCEPT_BROADCAST;
+ break;
+ case BNX2X_RX_MODE_PROMISC:
+ req->rx_mask = VFPF_RX_MASK_ACCEPT_ALL_UNICAST;
+ req->rx_mask |= VFPF_RX_MASK_ACCEPT_ALL_MULTICAST;
+ req->rx_mask |= VFPF_RX_MASK_ACCEPT_BROADCAST;
+ break;
+ default:
+ BNX2X_ERR("BAD rx mode (%d)\n", mode);
+ return -EINVAL;
+ }
+
+ req->flags |= VFPF_SET_Q_FILTERS_RX_MASK_CHANGED;
+ req->vf_qid = 0;
+
+ /* add list termination tlv */
+ bnx2x_add_tlv(bp, req, req->first_tlv.tl.length, CHANNEL_TLV_LIST_END,
+ sizeof(struct channel_list_end_tlv));
+
+ /* output tlvs list */
+ bnx2x_dp_tlv_list(bp, req);
+
+ rc = bnx2x_send_msg2pf(bp, &resp->hdr.status, bp->vf2pf_mbox_mapping);
+ if (rc)
+ BNX2X_ERR("Sending a message failed: %d\n", rc);
+
+ if (resp->hdr.status != PFVF_STATUS_SUCCESS) {
+ BNX2X_ERR("Set Rx mode failed: %d\n", resp->hdr.status);
+ return -EINVAL;
+ }
+
+ return rc;
+}
+
/* General service functions */
static void storm_memset_vf_mbx_ack(struct bnx2x *bp, u16 abs_fid)
{
diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.h b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.h
index 9f07ada..21d2985 100644
--- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.h
+++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_vfpf.h
@@ -18,6 +18,8 @@
#ifndef VF_PF_IF_H
#define VF_PF_IF_H
+#ifdef CONFIG_BNX2X_SRIOV
+
/* Common definitions for all HVs */
struct vf_pf_resc_request {
u8 num_rxqs;
@@ -353,4 +355,5 @@ enum channel_tlvs {
CHANNEL_TLV_MAX
};
+#endif /* CONFIG_BNX2X_SRIOV */
#endif /* VF_PF_IF_H */
--
1.7.9.GIT
^ permalink raw reply related
* Re: [PATCH 2/2] ipv6: fix packet corruption when Dest/RT2 options are used
From: Nicolas Dichtel @ 2013-01-07 10:49 UTC (permalink / raw)
To: Romain KUNTZ; +Cc: netdev, yoshfuji, davem, Steffen Klassert
In-Reply-To: <C7895CAA-0AF7-4EED-B9E7-9D8E4A21442B@ipflavors.com>
Le 05/01/2013 17:19, Romain KUNTZ a écrit :
> Commit 299b0767 (ipv6: Fix IPsec slowpath fragmentation problem)
Add Steffen into CC, he is the author of this patch and the IPsec
maintainer.
> has introduced a bug that provokes corrupted packets when Destination
> Options or Routing Header Type 2 are used (such as with Mobile IPv6):
> rt->rt6i_nfheader_len should be substracted to rt->dst.header_len,
> and not to exthdrlen.
>
> This patch reverts to the original and correct behavior. Successfully
> tested with and without IPsec activated for MH packets.
>
> Signed-off-by: Romain Kuntz <r.kuntz@ipflavors.com>
> ---
> net/ipv6/ip6_output.c | 4 ++--
> 1 files changed, 2 insertions(+), 2 deletions(-)
>
> diff --git a/net/ipv6/ip6_output.c b/net/ipv6/ip6_output.c
> index 5552d13..0c7c03d 100644
> --- a/net/ipv6/ip6_output.c
> +++ b/net/ipv6/ip6_output.c
> @@ -1213,10 +1213,10 @@ int ip6_append_data(struct sock *sk, int getfrag(void *from, char *to,
> if (dst_allfrag(rt->dst.path))
> cork->flags |= IPCORK_ALLFRAG;
> cork->length = 0;
> - exthdrlen = (opt ? opt->opt_flen : 0) - rt->rt6i_nfheader_len;
> + exthdrlen = (opt ? opt->opt_flen : 0);
> length += exthdrlen;
> transhdrlen += exthdrlen;
> - dst_exthdrlen = rt->dst.header_len;
> + dst_exthdrlen = rt->dst.header_len - rt->rt6i_nfheader_len;
> } else {
> rt = (struct rt6_info *)cork->dst;
> fl6 = &inet->cork.fl.u.ip6;
>
^ permalink raw reply
* Re: [PATCH repost] net,wireless: check against default_ethtool_ops
From: Jiri Pirko @ 2013-01-07 11:11 UTC (permalink / raw)
To: Stanislaw Gruszka
Cc: netdev, David S. Miller, Eric Dumazet, Ben Greear,
Bjørn Mork, linux-wireless, Ben Hutchings
In-Reply-To: <20130107104413.GB6931@redhat.com>
Mon, Jan 07, 2013 at 11:44:14AM CET, sgruszka@redhat.com wrote:
>On Mon, Jan 07, 2013 at 11:23:07AM +0100, Jiri Pirko wrote:
>> >-static const struct ethtool_ops default_ethtool_ops;
>> >+const struct ethtool_ops default_ethtool_ops;
>> >+EXPORT_SYMBOL_GPL(default_ethtool_ops);
>>
>> I think that default_ethtool_ops should stay static. Wouldn't it be
>> nicer to introduce a helper like:
>>
>> bool dev_has_default_ethtool_ops(struct net_device *dev)
>> {
>> return dev->ethtool_ops == &default_ethtool_ops;
>> }
>
>Then I still have to export this function. So with your approch, number
>of exported symbols will be the same, but there will be few more lines
>of code.
I think it's always better to add few more lines in order to prevent possible
confusion which exporting default_ethtool_ops might introduce...
>
>Stanislaw
^ permalink raw reply
* pull request: batman-adv 2013-01-07
From: Antonio Quartulli @ 2013-01-07 11:11 UTC (permalink / raw)
To: davem; +Cc: netdev, b.a.t.m.a.n
here are two harmless "fixes" intended for net:
one is fixing the versioning number in order to keep it in sync with the year of
release and the other simply updates the copyright years in each and every file.
Please pull or let me know if you find any problem.
Thanks a lot,
Antonio
The following changes since commit c7e2e1d72ed7707239d20525e0ebcad7e3303659:
ipv4: fix NULL checking in devinet_ioctl() (2013-01-06 21:11:18 -0800)
are available in the git repository at:
git://git.open-mesh.org/linux-merge.git tags/batman-adv-fix-for-davem
for you to fetch changes up to d5c184eec815d28d042683f578f6d93224d9dfa9:
batman-adv: update copyright years (2013-01-07 11:43:19 +0100)
----------------------------------------------------------------
Included fixes are:
- Fix version number to keep consistency with the year of release
- Update copyright years to 2013 in each file
----------------------------------------------------------------
Antonio Quartulli (2):
batman-adv: Start new development cycle
batman-adv: update copyright years
net/batman-adv/bat_algo.h | 2 +-
net/batman-adv/bat_iv_ogm.c | 2 +-
net/batman-adv/bitarray.c | 2 +-
net/batman-adv/bitarray.h | 2 +-
net/batman-adv/bridge_loop_avoidance.c | 2 +-
net/batman-adv/bridge_loop_avoidance.h | 2 +-
net/batman-adv/debugfs.c | 2 +-
net/batman-adv/debugfs.h | 2 +-
net/batman-adv/distributed-arp-table.c | 2 +-
net/batman-adv/distributed-arp-table.h | 2 +-
net/batman-adv/gateway_client.c | 2 +-
net/batman-adv/gateway_client.h | 2 +-
net/batman-adv/gateway_common.c | 2 +-
net/batman-adv/gateway_common.h | 2 +-
net/batman-adv/hard-interface.c | 2 +-
net/batman-adv/hard-interface.h | 2 +-
net/batman-adv/hash.c | 2 +-
net/batman-adv/hash.h | 2 +-
net/batman-adv/icmp_socket.c | 2 +-
net/batman-adv/icmp_socket.h | 2 +-
net/batman-adv/main.c | 2 +-
net/batman-adv/main.h | 4 ++--
net/batman-adv/originator.c | 2 +-
net/batman-adv/originator.h | 2 +-
net/batman-adv/packet.h | 2 +-
net/batman-adv/ring_buffer.c | 2 +-
net/batman-adv/ring_buffer.h | 2 +-
net/batman-adv/routing.c | 2 +-
net/batman-adv/routing.h | 2 +-
net/batman-adv/send.c | 2 +-
net/batman-adv/send.h | 2 +-
net/batman-adv/soft-interface.c | 2 +-
net/batman-adv/soft-interface.h | 2 +-
net/batman-adv/sysfs.c | 2 +-
net/batman-adv/sysfs.h | 2 +-
net/batman-adv/translation-table.c | 2 +-
net/batman-adv/translation-table.h | 2 +-
net/batman-adv/types.h | 2 +-
net/batman-adv/unicast.c | 2 +-
net/batman-adv/unicast.h | 2 +-
net/batman-adv/vis.c | 2 +-
net/batman-adv/vis.h | 2 +-
42 files changed, 43 insertions(+), 43 deletions(-)
^ permalink raw reply
* [PATCH 1/2] batman-adv: Start new development cycle
From: Antonio Quartulli @ 2013-01-07 11:11 UTC (permalink / raw)
To: davem; +Cc: netdev, b.a.t.m.a.n, Antonio Quartulli, Marek Lindner
In-Reply-To: <1357557088-17866-1-git-send-email-ordex@autistici.org>
Signed-off-by: Antonio Quartulli <ordex@autistici.org>
Signed-off-by: Marek Lindner <lindner_marek@yahoo.de>
---
net/batman-adv/main.h | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/net/batman-adv/main.h b/net/batman-adv/main.h
index 2f85577..5d994a6 100644
--- a/net/batman-adv/main.h
+++ b/net/batman-adv/main.h
@@ -26,7 +26,7 @@
#define BATADV_DRIVER_DEVICE "batman-adv"
#ifndef BATADV_SOURCE_VERSION
-#define BATADV_SOURCE_VERSION "2012.5.0"
+#define BATADV_SOURCE_VERSION "2013.0.0"
#endif
/* B.A.T.M.A.N. parameters */
--
1.8.0.2
^ permalink raw reply related
* [PATCH 2/2] batman-adv: update copyright years
From: Antonio Quartulli @ 2013-01-07 11:11 UTC (permalink / raw)
To: davem; +Cc: netdev, b.a.t.m.a.n, Antonio Quartulli, Marek Lindner
In-Reply-To: <1357557088-17866-1-git-send-email-ordex@autistici.org>
Signed-off-by: Antonio Quartulli <ordex@autistici.org>
Signed-off-by: Marek Lindner <lindner_marek@yahoo.de>
---
net/batman-adv/bat_algo.h | 2 +-
net/batman-adv/bat_iv_ogm.c | 2 +-
net/batman-adv/bitarray.c | 2 +-
net/batman-adv/bitarray.h | 2 +-
net/batman-adv/bridge_loop_avoidance.c | 2 +-
net/batman-adv/bridge_loop_avoidance.h | 2 +-
net/batman-adv/debugfs.c | 2 +-
net/batman-adv/debugfs.h | 2 +-
net/batman-adv/distributed-arp-table.c | 2 +-
net/batman-adv/distributed-arp-table.h | 2 +-
net/batman-adv/gateway_client.c | 2 +-
net/batman-adv/gateway_client.h | 2 +-
net/batman-adv/gateway_common.c | 2 +-
net/batman-adv/gateway_common.h | 2 +-
net/batman-adv/hard-interface.c | 2 +-
net/batman-adv/hard-interface.h | 2 +-
net/batman-adv/hash.c | 2 +-
net/batman-adv/hash.h | 2 +-
net/batman-adv/icmp_socket.c | 2 +-
net/batman-adv/icmp_socket.h | 2 +-
net/batman-adv/main.c | 2 +-
net/batman-adv/main.h | 2 +-
net/batman-adv/originator.c | 2 +-
net/batman-adv/originator.h | 2 +-
net/batman-adv/packet.h | 2 +-
net/batman-adv/ring_buffer.c | 2 +-
net/batman-adv/ring_buffer.h | 2 +-
net/batman-adv/routing.c | 2 +-
net/batman-adv/routing.h | 2 +-
net/batman-adv/send.c | 2 +-
net/batman-adv/send.h | 2 +-
net/batman-adv/soft-interface.c | 2 +-
net/batman-adv/soft-interface.h | 2 +-
net/batman-adv/sysfs.c | 2 +-
net/batman-adv/sysfs.h | 2 +-
net/batman-adv/translation-table.c | 2 +-
net/batman-adv/translation-table.h | 2 +-
net/batman-adv/types.h | 2 +-
net/batman-adv/unicast.c | 2 +-
net/batman-adv/unicast.h | 2 +-
net/batman-adv/vis.c | 2 +-
net/batman-adv/vis.h | 2 +-
42 files changed, 42 insertions(+), 42 deletions(-)
diff --git a/net/batman-adv/bat_algo.h b/net/batman-adv/bat_algo.h
index a0ba3bf..a4808c2 100644
--- a/net/batman-adv/bat_algo.h
+++ b/net/batman-adv/bat_algo.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2011-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2011-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/bat_iv_ogm.c b/net/batman-adv/bat_iv_ogm.c
index 7d02ebd..3581e2f 100644
--- a/net/batman-adv/bat_iv_ogm.c
+++ b/net/batman-adv/bat_iv_ogm.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/bitarray.c b/net/batman-adv/bitarray.c
index 5453b17..9739824 100644
--- a/net/batman-adv/bitarray.c
+++ b/net/batman-adv/bitarray.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2006-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2006-2013 B.A.T.M.A.N. contributors:
*
* Simon Wunderlich, Marek Lindner
*
diff --git a/net/batman-adv/bitarray.h b/net/batman-adv/bitarray.h
index cebaae7..a81b932 100644
--- a/net/batman-adv/bitarray.h
+++ b/net/batman-adv/bitarray.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2006-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2006-2013 B.A.T.M.A.N. contributors:
*
* Simon Wunderlich, Marek Lindner
*
diff --git a/net/batman-adv/bridge_loop_avoidance.c b/net/batman-adv/bridge_loop_avoidance.c
index 5aebe93..5348a4d 100644
--- a/net/batman-adv/bridge_loop_avoidance.c
+++ b/net/batman-adv/bridge_loop_avoidance.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2011-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2011-2013 B.A.T.M.A.N. contributors:
*
* Simon Wunderlich
*
diff --git a/net/batman-adv/bridge_loop_avoidance.h b/net/batman-adv/bridge_loop_avoidance.h
index 196d9a0..dea2fbc 100644
--- a/net/batman-adv/bridge_loop_avoidance.h
+++ b/net/batman-adv/bridge_loop_avoidance.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2011-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2011-2013 B.A.T.M.A.N. contributors:
*
* Simon Wunderlich
*
diff --git a/net/batman-adv/debugfs.c b/net/batman-adv/debugfs.c
index 6f58ddd..f6a18e1 100644
--- a/net/batman-adv/debugfs.c
+++ b/net/batman-adv/debugfs.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2010-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/debugfs.h b/net/batman-adv/debugfs.h
index 3319e1f..f8c3849 100644
--- a/net/batman-adv/debugfs.h
+++ b/net/batman-adv/debugfs.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2010-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/distributed-arp-table.c b/net/batman-adv/distributed-arp-table.c
index 8e1d89d..7485a78 100644
--- a/net/batman-adv/distributed-arp-table.c
+++ b/net/batman-adv/distributed-arp-table.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2011-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2011-2013 B.A.T.M.A.N. contributors:
*
* Antonio Quartulli
*
diff --git a/net/batman-adv/distributed-arp-table.h b/net/batman-adv/distributed-arp-table.h
index d060c03..125c8c6 100644
--- a/net/batman-adv/distributed-arp-table.h
+++ b/net/batman-adv/distributed-arp-table.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2011-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2011-2013 B.A.T.M.A.N. contributors:
*
* Antonio Quartulli
*
diff --git a/net/batman-adv/gateway_client.c b/net/batman-adv/gateway_client.c
index dd07c7e..074107f 100644
--- a/net/batman-adv/gateway_client.c
+++ b/net/batman-adv/gateway_client.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2009-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/gateway_client.h b/net/batman-adv/gateway_client.h
index f0d129e..039902d 100644
--- a/net/batman-adv/gateway_client.h
+++ b/net/batman-adv/gateway_client.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2009-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/gateway_common.c b/net/batman-adv/gateway_common.c
index 9001208..84bb2b1 100644
--- a/net/batman-adv/gateway_common.c
+++ b/net/batman-adv/gateway_common.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2009-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/gateway_common.h b/net/batman-adv/gateway_common.h
index 13697f6..509b2bf 100644
--- a/net/batman-adv/gateway_common.h
+++ b/net/batman-adv/gateway_common.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2009-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/hard-interface.c b/net/batman-adv/hard-interface.c
index f1d37cd..78cf350 100644
--- a/net/batman-adv/hard-interface.c
+++ b/net/batman-adv/hard-interface.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/hard-interface.h b/net/batman-adv/hard-interface.h
index 3732366..308437d 100644
--- a/net/batman-adv/hard-interface.h
+++ b/net/batman-adv/hard-interface.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/hash.c b/net/batman-adv/hash.c
index 15a849c..7198daf 100644
--- a/net/batman-adv/hash.c
+++ b/net/batman-adv/hash.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2006-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2006-2013 B.A.T.M.A.N. contributors:
*
* Simon Wunderlich, Marek Lindner
*
diff --git a/net/batman-adv/hash.h b/net/batman-adv/hash.h
index e053339..4654354 100644
--- a/net/batman-adv/hash.h
+++ b/net/batman-adv/hash.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2006-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2006-2013 B.A.T.M.A.N. contributors:
*
* Simon Wunderlich, Marek Lindner
*
diff --git a/net/batman-adv/icmp_socket.c b/net/batman-adv/icmp_socket.c
index 87ca809..0ba6c89 100644
--- a/net/batman-adv/icmp_socket.c
+++ b/net/batman-adv/icmp_socket.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/icmp_socket.h b/net/batman-adv/icmp_socket.h
index 29443a1..1fcca37 100644
--- a/net/batman-adv/icmp_socket.h
+++ b/net/batman-adv/icmp_socket.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/main.c b/net/batman-adv/main.c
index f65a222..21fe698 100644
--- a/net/batman-adv/main.c
+++ b/net/batman-adv/main.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/main.h b/net/batman-adv/main.h
index 5d994a6..9925cf1 100644
--- a/net/batman-adv/main.h
+++ b/net/batman-adv/main.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/originator.c b/net/batman-adv/originator.c
index 8c32cf1..397110f 100644
--- a/net/batman-adv/originator.c
+++ b/net/batman-adv/originator.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2009-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2009-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/originator.h b/net/batman-adv/originator.h
index 9778e65..286bf74 100644
--- a/net/batman-adv/originator.h
+++ b/net/batman-adv/originator.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/packet.h b/net/batman-adv/packet.h
index cb6405bf..ed0aa89 100644
--- a/net/batman-adv/packet.h
+++ b/net/batman-adv/packet.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/ring_buffer.c b/net/batman-adv/ring_buffer.c
index c8f61e3..ccab0bb 100644
--- a/net/batman-adv/ring_buffer.c
+++ b/net/batman-adv/ring_buffer.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/ring_buffer.h b/net/batman-adv/ring_buffer.h
index fda8c17..3f92ae2 100644
--- a/net/batman-adv/ring_buffer.h
+++ b/net/batman-adv/ring_buffer.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/routing.c b/net/batman-adv/routing.c
index 1aa1722..93a33dc 100644
--- a/net/batman-adv/routing.c
+++ b/net/batman-adv/routing.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/routing.h b/net/batman-adv/routing.h
index 9262279..99eeafa 100644
--- a/net/batman-adv/routing.h
+++ b/net/batman-adv/routing.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/send.c b/net/batman-adv/send.c
index 4425af9..989d3c68 100644
--- a/net/batman-adv/send.c
+++ b/net/batman-adv/send.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/send.h b/net/batman-adv/send.h
index 0078dec..38e662f 100644
--- a/net/batman-adv/send.h
+++ b/net/batman-adv/send.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/soft-interface.c b/net/batman-adv/soft-interface.c
index 6b548fd..e7dcb40 100644
--- a/net/batman-adv/soft-interface.c
+++ b/net/batman-adv/soft-interface.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/soft-interface.h b/net/batman-adv/soft-interface.h
index 07a08fe..43182e5 100644
--- a/net/batman-adv/soft-interface.h
+++ b/net/batman-adv/soft-interface.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/sysfs.c b/net/batman-adv/sysfs.c
index 84a55cb..afbba31 100644
--- a/net/batman-adv/sysfs.c
+++ b/net/batman-adv/sysfs.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2010-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/sysfs.h b/net/batman-adv/sysfs.h
index 3fd1412..479acf4 100644
--- a/net/batman-adv/sysfs.h
+++ b/net/batman-adv/sysfs.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2010-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner
*
diff --git a/net/batman-adv/translation-table.c b/net/batman-adv/translation-table.c
index 22457a7..3b2dc5f 100644
--- a/net/batman-adv/translation-table.c
+++ b/net/batman-adv/translation-table.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich, Antonio Quartulli
*
diff --git a/net/batman-adv/translation-table.h b/net/batman-adv/translation-table.h
index 46d4451..ab8e683 100644
--- a/net/batman-adv/translation-table.h
+++ b/net/batman-adv/translation-table.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich, Antonio Quartulli
*
diff --git a/net/batman-adv/types.h b/net/batman-adv/types.h
index ae9ac9a..a656707 100644
--- a/net/batman-adv/types.h
+++ b/net/batman-adv/types.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2007-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2007-2013 B.A.T.M.A.N. contributors:
*
* Marek Lindner, Simon Wunderlich
*
diff --git a/net/batman-adv/unicast.c b/net/batman-adv/unicast.c
index 10aff49..9c8094a 100644
--- a/net/batman-adv/unicast.c
+++ b/net/batman-adv/unicast.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2010-2013 B.A.T.M.A.N. contributors:
*
* Andreas Langer
*
diff --git a/net/batman-adv/unicast.h b/net/batman-adv/unicast.h
index 61abba5..429cf8a 100644
--- a/net/batman-adv/unicast.h
+++ b/net/batman-adv/unicast.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2010-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2010-2013 B.A.T.M.A.N. contributors:
*
* Andreas Langer
*
diff --git a/net/batman-adv/vis.c b/net/batman-adv/vis.c
index 0f65a9d..9049a55 100644
--- a/net/batman-adv/vis.c
+++ b/net/batman-adv/vis.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2008-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2008-2013 B.A.T.M.A.N. contributors:
*
* Simon Wunderlich
*
diff --git a/net/batman-adv/vis.h b/net/batman-adv/vis.h
index 873282f..ad92b0e 100644
--- a/net/batman-adv/vis.h
+++ b/net/batman-adv/vis.h
@@ -1,4 +1,4 @@
-/* Copyright (C) 2008-2012 B.A.T.M.A.N. contributors:
+/* Copyright (C) 2008-2013 B.A.T.M.A.N. contributors:
*
* Simon Wunderlich, Marek Lindner
*
--
1.8.0.2
^ permalink raw reply related
* Re: [PATCH] drivers/net/wireless/iwlegacy: use strlcpy instead of strncpy
From: Stanislaw Gruszka @ 2013-01-07 11:17 UTC (permalink / raw)
To: Chen Gang; +Cc: linville, linux-wireless, netdev
In-Reply-To: <50EA5246.8060206@asianux.com>
On Mon, Jan 07, 2013 at 12:42:46PM +0800, Chen Gang wrote:
>
> The fields must be null-terminated, or simple_strtoul will cause issue.
>
> Signed-off-by: Chen Gang <gang.chen@asianux.com>
ACK
^ permalink raw reply
* Re: [PATCH 1/2] ipv6: avoid blackhole and prohibited entries upon prefix purge [v2]
From: Romain KUNTZ @ 2013-01-07 11:30 UTC (permalink / raw)
To: nicolas.dichtel; +Cc: netdev, Eric Dumazet, yoshfuji, davem, Romain KUNTZ
In-Reply-To: <50EAA28B.1080300@6wind.com>
Hello Nicolas,
On Jan 7, 2013, at 11:25 , Nicolas Dichtel <nicolas.dichtel@6wind.com> wrote:
> Le 05/01/2013 22:44, Romain KUNTZ a écrit :
>> Mobile IPv6 provokes a kernel Oops since commit 64c6d08e (ipv6:
>> del unreachable route when an addr is deleted on lo), because
>> ip6_route_lookup() may also return blackhole and prohibited
>> entry. However, these entries have a NULL rt6i_table argument,
>> which provokes an Oops in __ip6_del_rt() when trying to lock
>> rt6i_table->tb6_lock.
>>
>> Beside, when purging a prefix, blakhole and prohibited entries
>> should not be selected because they are not what we are looking
>> for.
>>
>> We fix this by adding two new lookup flags (RT6_LOOKUP_F_NO_BLK_HOLE
>> and RT6_LOOKUP_F_NO_PROHIBIT) in order to ensure that such entries
>> are skipped during lookup and that the correct entry is returned.
>>
>> [v2]: use 'goto out;' instead of 'goto again;' to avoid unnecessary
>> oprations on rt (as suggested by Eric Dumazet).
>>
>> Signed-off-by: Romain Kuntz <r.kuntz@ipflavors.com>
>> ---
>> include/net/ip6_route.h | 2 ++
>> net/ipv6/addrconf.c | 4 +++-
>> net/ipv6/fib6_rules.c | 4 ++++
>> 3 files changed, 9 insertions(+), 1 deletions(-)
>>
>> diff --git a/include/net/ip6_route.h b/include/net/ip6_route.h
>> index 27d8318..3c93743 100644
>> --- a/include/net/ip6_route.h
>> +++ b/include/net/ip6_route.h
>> @@ -30,6 +30,8 @@ struct route_info {
>> #define RT6_LOOKUP_F_SRCPREF_TMP 0x00000008
>> #define RT6_LOOKUP_F_SRCPREF_PUBLIC 0x00000010
>> #define RT6_LOOKUP_F_SRCPREF_COA 0x00000020
>> +#define RT6_LOOKUP_F_NO_BLK_HOLE 0x00000040
>> +#define RT6_LOOKUP_F_NO_PROHIBIT 0x00000080
>>
>> /*
>> * rt6_srcprefs2flags() and rt6_flags2srcprefs() translate
>> diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c
>> index 408cac4a..1891e23 100644
>> --- a/net/ipv6/addrconf.c
>> +++ b/net/ipv6/addrconf.c
>> @@ -948,7 +948,9 @@ static void ipv6_del_addr(struct inet6_ifaddr *ifp)
>> fl6.flowi6_oif = ifp->idev->dev->ifindex;
>> fl6.daddr = prefix;
>> rt = (struct rt6_info *)ip6_route_lookup(net, &fl6,
>> - RT6_LOOKUP_F_IFACE);
>> + RT6_LOOKUP_F_IFACE |
>> + RT6_LOOKUP_F_NO_BLK_HOLE |
>> + RT6_LOOKUP_F_NO_PROHIBIT);
>>
>> if (rt != net->ipv6.ip6_null_entry &&
> Is it not simpler to test the result here (net->ipv6.ip6_blk_hole_entry and
> net->ipv6.ip6_prohibit_entry) like for the null_entry?
> It will also avoid adding more flags.
Your proposal would only solve part of the problem (the Oops in __ip6_del_rt()). Another problem here is that blackhole and prohibited rules should not be selected when trying to purge a prefix (correct me if I'm wrong) because they are not what we are looking for. This can prevent the targeted prefix from being purged.
Thank you,
Romain
^ permalink raw reply
* Re: [PATCH repost] net,wireless: check against default_ethtool_ops
From: Stanislaw Gruszka @ 2013-01-07 11:20 UTC (permalink / raw)
To: Jiri Pirko
Cc: netdev, David S. Miller, Eric Dumazet, Ben Greear,
Bjørn Mork, linux-wireless, Ben Hutchings
In-Reply-To: <20130107111108.GB1587@minipsycho.orion>
On Mon, Jan 07, 2013 at 12:11:08PM +0100, Jiri Pirko wrote:
> Mon, Jan 07, 2013 at 11:44:14AM CET, sgruszka@redhat.com wrote:
> >On Mon, Jan 07, 2013 at 11:23:07AM +0100, Jiri Pirko wrote:
> >> >-static const struct ethtool_ops default_ethtool_ops;
> >> >+const struct ethtool_ops default_ethtool_ops;
> >> >+EXPORT_SYMBOL_GPL(default_ethtool_ops);
> >>
> >> I think that default_ethtool_ops should stay static. Wouldn't it be
> >> nicer to introduce a helper like:
> >>
> >> bool dev_has_default_ethtool_ops(struct net_device *dev)
> >> {
> >> return dev->ethtool_ops == &default_ethtool_ops;
> >> }
> >
> >Then I still have to export this function. So with your approch, number
> >of exported symbols will be the same, but there will be few more lines
> >of code.
>
> I think it's always better to add few more lines in order to prevent possible
> confusion which exporting default_ethtool_ops might introduce...
What possible confusion it might cause?
Stanislaw
^ permalink raw reply
* Re: [PATCH repost] net,wireless: check against default_ethtool_ops
From: Jiri Pirko @ 2013-01-07 11:57 UTC (permalink / raw)
To: Stanislaw Gruszka
Cc: netdev-u79uwXL29TY76Z2rM5mHXA, David S. Miller, Eric Dumazet,
Ben Greear, Bjørn Mork,
linux-wireless-u79uwXL29TY76Z2rM5mHXA, Ben Hutchings
In-Reply-To: <20130107112012.GE6931-H+wXaHxf7aLQT0dZR+AlfA@public.gmane.org>
Mon, Jan 07, 2013 at 12:20:12PM CET, sgruszka-H+wXaHxf7aLQT0dZR+AlfA@public.gmane.org wrote:
>On Mon, Jan 07, 2013 at 12:11:08PM +0100, Jiri Pirko wrote:
>> Mon, Jan 07, 2013 at 11:44:14AM CET, sgruszka-H+wXaHxf7aLQT0dZR+AlfA@public.gmane.org wrote:
>> >On Mon, Jan 07, 2013 at 11:23:07AM +0100, Jiri Pirko wrote:
>> >> >-static const struct ethtool_ops default_ethtool_ops;
>> >> >+const struct ethtool_ops default_ethtool_ops;
>> >> >+EXPORT_SYMBOL_GPL(default_ethtool_ops);
>> >>
>> >> I think that default_ethtool_ops should stay static. Wouldn't it be
>> >> nicer to introduce a helper like:
>> >>
>> >> bool dev_has_default_ethtool_ops(struct net_device *dev)
>> >> {
>> >> return dev->ethtool_ops == &default_ethtool_ops;
>> >> }
>> >
>> >Then I still have to export this function. So with your approch, number
>> >of exported symbols will be the same, but there will be few more lines
>> >of code.
>>
>> I think it's always better to add few more lines in order to prevent possible
>> confusion which exporting default_ethtool_ops might introduce...
>
>What possible confusion it might cause?
Someone would possibly like to do:
dev->netdev_ops = &default_ethtool_ops
in drivers for example...
+ I just do not think that exporting structs is the correct way in order
to do anything.
>
>Stanislaw
--
To unsubscribe from this list: send the line "unsubscribe linux-wireless" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
^ permalink raw reply
* Re: ppoll() stuck on POLLIN while TCP peer is sending
From: Mel Gorman @ 2013-01-07 12:25 UTC (permalink / raw)
To: Eric Wong
Cc: linux-mm, netdev, linux-kernel, Rik van Riel, Minchan Kim,
Eric Dumazet, Andrew Morton, Linus Torvalds
In-Reply-To: <20130106120700.GA24671@dcvr.yhbt.net>
On Sun, Jan 06, 2013 at 12:07:00PM +0000, Eric Wong wrote:
> Mel Gorman <mgorman@suse.de> wrote:
> > Using a 3.7.1 or 3.8-rc2 kernel, can you reproduce the problem and then
> > answer the following questions please?
>
> This is on my main machine running 3.8-rc2
>
> > 1. What are the contents of /proc/vmstat at the time it is stuck?
>
> ===> /proc/vmstat <===
According to this, THP is barely being used -- only 24 THP pages at the time
and the LRU lists are dominated by file pages. The isolated and throttled
counters look fine. There is a lot of memory currently under writeback and
a large number of dirty pages are reaching the end of the LRU list which
is inefficient but does not account for the reported bug.
> > 2. What are the contents of /proc/PID/stack for every toosleepy
> > process when they are stuck?
>
> pid and tid stack info, 28018 is the thread I used to automate
> reporting (pushed to git://bogomips.org/toosleepy.git)
>
> ===> 28014[28014]/stack <===
> [<ffffffff8105a97b>] futex_wait_queue_me+0xb7/0xd2
> [<ffffffff8105b7fc>] futex_wait+0xf6/0x1f6
> [<ffffffff811bb3af>] cpumask_next_and+0x2b/0x37
> [<ffffffff8104ebfa>] select_task_rq_fair+0x518/0x59a
> [<ffffffff8105c8f1>] do_futex+0xa9/0x88f
> [<ffffffff810509a4>] check_preempt_wakeup+0x10d/0x1a7
> [<ffffffff8104757d>] check_preempt_curr+0x25/0x62
> [<ffffffff8104d4cc>] wake_up_new_task+0x96/0xc2
> [<ffffffff8105d1e9>] sys_futex+0x112/0x14d
> [<ffffffff81322a49>] stub_clone+0x69/0x90
> [<ffffffff81322769>] system_call_fastpath+0x16/0x1b
> [<ffffffffffffffff>] 0xffffffffffffffff
Looks ok.
> ===> 28014[28015]/stack <===
> [<ffffffff812ae316>] dev_hard_start_xmit+0x281/0x3f1
> [<ffffffff81041010>] add_wait_queue+0x14/0x40
> [<ffffffff810de0bc>] poll_schedule_timeout+0x43/0x5d
> [<ffffffff810deb46>] do_sys_poll+0x314/0x39b
> [<ffffffff810de220>] pollwake+0x0/0x4e
> [<ffffffff8129fc1d>] release_sock+0xe5/0x11b
> [<ffffffff812d7f61>] tcp_recvmsg+0x713/0x846
> [<ffffffff812f432c>] inet_recvmsg+0x64/0x75
> [<ffffffff8129a26b>] sock_recvmsg+0x86/0x9e
> [<ffffffff8100541c>] emulate_vsyscall+0x1e6/0x28e
> [<ffffffff8129a3bc>] sockfd_lookup_light+0x1a/0x50
> [<ffffffff8129c18b>] sys_recvfrom+0x110/0x128
> [<ffffffff81000e34>] __switch_to+0x235/0x3c5
> [<ffffffff810ca402>] kmem_cache_free+0x32/0xb9
> [<ffffffff810b809d>] remove_vma+0x44/0x4c
> [<ffffffff810df0a5>] sys_ppoll+0xaf/0x123
> [<ffffffff81322769>] system_call_fastpath+0x16/0x1b
> [<ffffffffffffffff>] 0xffffffffffffffff
Polling waiting for data, looks ok to me.
> ===> 28014[28016]/stack <===
> [<ffffffff812ae7ad>] dev_queue_xmit+0x327/0x336
> [<ffffffff8102cb9f>] _local_bh_enable_ip+0x7a/0x8b
> [<ffffffff81041010>] add_wait_queue+0x14/0x40
> [<ffffffff810de0bc>] poll_schedule_timeout+0x43/0x5d
> [<ffffffff810deb46>] do_sys_poll+0x314/0x39b
> [<ffffffff810de220>] pollwake+0x0/0x4e
> [<ffffffff8129fc1d>] release_sock+0xe5/0x11b
> [<ffffffff812d7f61>] tcp_recvmsg+0x713/0x846
> [<ffffffff812f432c>] inet_recvmsg+0x64/0x75
> [<ffffffff8129a26b>] sock_recvmsg+0x86/0x9e
> [<ffffffff8100541c>] emulate_vsyscall+0x1e6/0x28e
> [<ffffffff8129a3bc>] sockfd_lookup_light+0x1a/0x50
> [<ffffffff8129c18b>] sys_recvfrom+0x110/0x128
> [<ffffffff81000e34>] __switch_to+0x235/0x3c5
> [<ffffffff810df0a5>] sys_ppoll+0xaf/0x123
> [<ffffffff81322769>] system_call_fastpath+0x16/0x1b
> [<ffffffffffffffff>] 0xffffffffffffffff
Waiting on receive again.
> ===> 28014[28017]/stack <===
> [<ffffffff8129fc1d>] release_sock+0xe5/0x11b
> [<ffffffff812a642c>] sk_stream_wait_memory+0x1f7/0x1fc
> [<ffffffff81040d5e>] autoremove_wake_function+0x0/0x2a
> [<ffffffff812d8fc3>] tcp_sendmsg+0x710/0x86d
> [<ffffffff8129a33e>] sock_sendmsg+0x7b/0x93
> [<ffffffff8129a642>] sys_sendto+0xee/0x145
> [<ffffffff8129a3bc>] sockfd_lookup_light+0x1a/0x50
> [<ffffffff8129a668>] sys_sendto+0x114/0x145
> [<ffffffff81000e34>] __switch_to+0x235/0x3c5
> [<ffffffff81322769>] system_call_fastpath+0x16/0x1b
> [<ffffffffffffffff>] 0xffffffffffffffff
This seems to be the guy that's stuck. It's waiting for more memory for
the socket but who or what is allocating that memory? There are a few other
bugs from over the weekend that I want to take a look at so I did not dig
further or try to reproduce this bug yet. I'm adding Eric Dumazet back to
the cc in case he has the quick answer.
> ===> 28014[28018]/stack <===
> [<ffffffff8102b23e>] do_wait+0x1a6/0x21a
> [<ffffffff8104757d>] check_preempt_curr+0x25/0x62
> [<ffffffff8102b34a>] sys_wait4+0x98/0xb5
> [<ffffffff81026321>] do_fork+0x12c/0x1a7
> [<ffffffff810297b0>] child_wait_callback+0x0/0x48
> [<ffffffff8131c688>] page_fault+0x28/0x30
> [<ffffffff81322769>] system_call_fastpath+0x16/0x1b
> [<ffffffffffffffff>] 0xffffffffffffffff
>
> > 3. Can you do a sysrq+m and post the resulting dmesg?
>
> SysRq : Show Memory
> Mem-Info:
> DMA per-cpu:
> CPU 0: hi: 0, btch: 1 usd: 0
> CPU 1: hi: 0, btch: 1 usd: 0
> CPU 2: hi: 0, btch: 1 usd: 0
> CPU 3: hi: 0, btch: 1 usd: 0
> DMA32 per-cpu:
> CPU 0: hi: 186, btch: 31 usd: 4
> CPU 1: hi: 186, btch: 31 usd: 181
> CPU 2: hi: 186, btch: 31 usd: 46
> CPU 3: hi: 186, btch: 31 usd: 13
> Normal per-cpu:
> CPU 0: hi: 186, btch: 31 usd: 106
> CPU 1: hi: 186, btch: 31 usd: 183
> CPU 2: hi: 186, btch: 31 usd: 20
> CPU 3: hi: 186, btch: 31 usd: 76
> active_anon:85782 inactive_anon:25023 isolated_anon:0
> active_file:209440 inactive_file:2610279 isolated_file:0
> unevictable:0 dirty:696664 writeback:629020 unstable:0
> free:44152 slab_reclaimable:68414 slab_unreclaimable:14178
> mapped:6017 shmem:24101 pagetables:3136 bounce:0
> free_cma:0
> DMA free:15872kB min:84kB low:104kB high:124kB active_anon:0kB inactive_anon:0kB active_file:0kB inactive_file:0kB unevictable:0kB isolated(anon):0kB isolated(file):0kB present:15640kB managed:15896kB mlocked:0kB dirty:0kB writeback:0kB mapped:0kB shmem:0kB slab_reclaimable:0kB slab_unreclaimable:24kB kernel_stack:0kB pagetables:0kB unstable:0kB bounce:0kB free_cma:0kB writeback_tmp:0kB pages_scanned:0 all_unreclaimable? yes
> lowmem_reserve[]: 0 3132 12078 12078
> DMA32 free:85264kB min:17504kB low:21880kB high:26256kB active_anon:46808kB inactive_anon:21212kB active_file:122040kB inactive_file:2833064kB unevictable:0kB isolated(anon):0kB isolated(file):0kB present:3208020kB managed:3185856kB mlocked:0kB dirty:92120kB writeback:225356kB mapped:356kB shmem:6776kB slab_reclaimable:67156kB slab_unreclaimable:7412kB kernel_stack:80kB pagetables:816kB unstable:0kB bounce:0kB free_cma:0kB writeback_tmp:0kB pages_scanned:0 all_unreclaimable? no
> lowmem_reserve[]: 0 0 8946 8946
> Normal free:75472kB min:49988kB low:62484kB high:74980kB active_anon:296320kB inactive_anon:78880kB active_file:715720kB inactive_file:7608052kB unevictable:0kB isolated(anon):0kB isolated(file):0kB present:9160704kB managed:9084264kB mlocked:0kB dirty:2694536kB writeback:2290724kB mapped:23712kB shmem:89628kB slab_reclaimable:206500kB slab_unreclaimable:49276kB kernel_stack:2432kB pagetables:11728kB unstable:0kB bounce:0kB free_cma:0kB writeback_tmp:0kB pages_scanned:0 all_unreclaimable? no
> lowmem_reserve[]: 0 0 0 0
> DMA: 0*4kB 0*8kB 0*16kB 0*32kB 2*64kB (U) 1*128kB (U) 1*256kB (U) 0*512kB 1*1024kB (U) 1*2048kB (R) 3*4096kB (M) = 15872kB
> DMA32: 1681*4kB (UEM) 3196*8kB (UEM) 3063*16kB (UEM) 63*32kB (UEM) 0*64kB 0*128kB 0*256kB 0*512kB 0*1024kB 1*2048kB (R) 0*4096kB = 85364kB
> Normal: 8874*4kB (UEM) 1885*8kB (UEM) 581*16kB (UEM) 412*32kB (UM) 0*64kB 0*128kB 0*256kB 0*512kB 0*1024kB 1*2048kB (R) 0*4096kB = 75104kB
Nothing wrong there that I can see. The free list contents roughly match
up with the NR_FREE_PAGES counter so it doesn't look like an accounting
bug. However, an accounting bug could have broken the bisection and
found a different bug.
When taking pages straight off the buddy list like this patch does,
there is a danger that the watermarks will be broken resulting in a
livelock but the watermarks are checked properly and the free pages are
over the min watermark above.
There is this patch https://lkml.org/lkml/2013/1/6/219 but it is
unlikely that it has anything to do with your workload as it does not
use splice().
Right now it's difficult to see how the capture could be the source of
this bug but I'm not ruling it out either so try the following (untested
but should be ok) patch. It's not a proper revert, it just disables the
capture page logic to see if it's at fault.
diff --git a/mm/compaction.c b/mm/compaction.c
index 6b807e4..81a637d 100644
--- a/mm/compaction.c
+++ b/mm/compaction.c
@@ -1054,9 +1054,6 @@ static int compact_zone(struct zone *zone, struct compact_control *cc)
goto out;
}
}
-
- /* Capture a page now if it is a suitable size */
- compact_capture_page(cc);
}
out:
diff --git a/mm/page_alloc.c b/mm/page_alloc.c
index 4ba5e37..85d3f9d 100644
--- a/mm/page_alloc.c
+++ b/mm/page_alloc.c
@@ -2179,11 +2179,8 @@ __alloc_pages_direct_compact(gfp_t gfp_mask, unsigned int order,
contended_compaction, &page);
current->flags &= ~PF_MEMALLOC;
- /* If compaction captured a page, prep and use it */
- if (page) {
- prep_new_page(page, order, gfp_mask);
- goto got_page;
- }
+ /* capture page is disabled, this should be impossible */
+ BUG_ON(page);
if (*did_some_progress != COMPACT_SKIPPED) {
/* Page migration frees to the PCP lists but we want merging */
@@ -2195,7 +2192,6 @@ __alloc_pages_direct_compact(gfp_t gfp_mask, unsigned int order,
alloc_flags & ~ALLOC_NO_WATERMARKS,
preferred_zone, migratetype);
if (page) {
-got_page:
preferred_zone->compact_blockskip_flush = false;
preferred_zone->compact_considered = 0;
preferred_zone->compact_defer_shift = 0;
^ permalink raw reply related
* [patch net-next] ethtool: consolidate work with ethtool_ops
From: Jiri Pirko @ 2013-01-07 12:26 UTC (permalink / raw)
To: netdev; +Cc: davem, bhutchings, richardcochran, greearb, jeffrey.t.kirsher
No need to check if ethtool_ops == NULL since it can't be.
Use local variable "ops" in functions where it is present
instead of dev->ethtool_ops
Introduce local variable "ops" in functions where dev->ethtool_ops is used
many times.
Signed-off-by: Jiri Pirko <jiri@resnulli.us>
---
net/core/ethtool.c | 45 +++++++++++++++++++++------------------------
1 file changed, 21 insertions(+), 24 deletions(-)
diff --git a/net/core/ethtool.c b/net/core/ethtool.c
index a870543..08c213e 100644
--- a/net/core/ethtool.c
+++ b/net/core/ethtool.c
@@ -175,7 +175,7 @@ static int __ethtool_get_sset_count(struct net_device *dev, int sset)
if (sset == ETH_SS_FEATURES)
return ARRAY_SIZE(netdev_features_strings);
- if (ops && ops->get_sset_count && ops->get_strings)
+ if (ops->get_sset_count && ops->get_strings)
return ops->get_sset_count(dev, sset);
else
return -EOPNOTSUPP;
@@ -311,7 +311,7 @@ int __ethtool_get_settings(struct net_device *dev, struct ethtool_cmd *cmd)
{
ASSERT_RTNL();
- if (!dev->ethtool_ops || !dev->ethtool_ops->get_settings)
+ if (!dev->ethtool_ops->get_settings)
return -EOPNOTSUPP;
memset(cmd, 0, sizeof(struct ethtool_cmd));
@@ -355,7 +355,7 @@ static noinline_for_stack int ethtool_get_drvinfo(struct net_device *dev,
memset(&info, 0, sizeof(info));
info.cmd = ETHTOOL_GDRVINFO;
- if (ops && ops->get_drvinfo) {
+ if (ops->get_drvinfo) {
ops->get_drvinfo(dev, &info);
} else if (dev->dev.parent && dev->dev.parent->driver) {
strlcpy(info.bus_info, dev_name(dev->dev.parent),
@@ -370,7 +370,7 @@ static noinline_for_stack int ethtool_get_drvinfo(struct net_device *dev,
* this method of obtaining string set info is deprecated;
* Use ETHTOOL_GSSET_INFO instead.
*/
- if (ops && ops->get_sset_count) {
+ if (ops->get_sset_count) {
int rc;
rc = ops->get_sset_count(dev, ETH_SS_TEST);
@@ -383,9 +383,9 @@ static noinline_for_stack int ethtool_get_drvinfo(struct net_device *dev,
if (rc >= 0)
info.n_priv_flags = rc;
}
- if (ops && ops->get_regs_len)
+ if (ops->get_regs_len)
info.regdump_len = ops->get_regs_len(dev);
- if (ops && ops->get_eeprom_len)
+ if (ops->get_eeprom_len)
info.eedump_len = ops->get_eeprom_len(dev);
if (copy_to_user(useraddr, &info, sizeof(info)))
@@ -590,13 +590,14 @@ static noinline_for_stack int ethtool_set_rxfh_indir(struct net_device *dev,
struct ethtool_rxnfc rx_rings;
u32 user_size, dev_size, i;
u32 *indir;
+ const struct ethtool_ops *ops = dev->ethtool_ops;
int ret;
- if (!dev->ethtool_ops->get_rxfh_indir_size ||
- !dev->ethtool_ops->set_rxfh_indir ||
- !dev->ethtool_ops->get_rxnfc)
+ if (!ops->get_rxfh_indir_size || !ops->set_rxfh_indir ||
+ !ops->get_rxnfc)
return -EOPNOTSUPP;
- dev_size = dev->ethtool_ops->get_rxfh_indir_size(dev);
+
+ dev_size = ops->get_rxfh_indir_size(dev);
if (dev_size == 0)
return -EOPNOTSUPP;
@@ -613,7 +614,7 @@ static noinline_for_stack int ethtool_set_rxfh_indir(struct net_device *dev,
return -ENOMEM;
rx_rings.cmd = ETHTOOL_GRXRINGS;
- ret = dev->ethtool_ops->get_rxnfc(dev, &rx_rings, NULL);
+ ret = ops->get_rxnfc(dev, &rx_rings, NULL);
if (ret)
goto out;
@@ -639,7 +640,7 @@ static noinline_for_stack int ethtool_set_rxfh_indir(struct net_device *dev,
}
}
- ret = dev->ethtool_ops->set_rxfh_indir(dev, indir);
+ ret = ops->set_rxfh_indir(dev, indir);
out:
kfree(indir);
@@ -1082,9 +1083,10 @@ static int ethtool_phys_id(struct net_device *dev, void __user *useraddr)
{
struct ethtool_value id;
static bool busy;
+ const struct ethtool_ops *ops = dev->ethtool_ops;
int rc;
- if (!dev->ethtool_ops->set_phys_id)
+ if (ops->set_phys_id)
return -EOPNOTSUPP;
if (busy)
@@ -1093,7 +1095,7 @@ static int ethtool_phys_id(struct net_device *dev, void __user *useraddr)
if (copy_from_user(&id, useraddr, sizeof(id)))
return -EFAULT;
- rc = dev->ethtool_ops->set_phys_id(dev, ETHTOOL_ID_ACTIVE);
+ rc = ops->set_phys_id(dev, ETHTOOL_ID_ACTIVE);
if (rc < 0)
return rc;
@@ -1118,7 +1120,7 @@ static int ethtool_phys_id(struct net_device *dev, void __user *useraddr)
i = n;
do {
rtnl_lock();
- rc = dev->ethtool_ops->set_phys_id(dev,
+ rc = ops->set_phys_id(dev,
(i & 1) ? ETHTOOL_ID_OFF : ETHTOOL_ID_ON);
rtnl_unlock();
if (rc)
@@ -1133,7 +1135,7 @@ static int ethtool_phys_id(struct net_device *dev, void __user *useraddr)
dev_put(dev);
busy = false;
- (void)dev->ethtool_ops->set_phys_id(dev, ETHTOOL_ID_INACTIVE);
+ (void) ops->set_phys_id(dev, ETHTOOL_ID_INACTIVE);
return rc;
}
@@ -1275,7 +1277,7 @@ static int ethtool_get_dump_flag(struct net_device *dev,
struct ethtool_dump dump;
const struct ethtool_ops *ops = dev->ethtool_ops;
- if (!dev->ethtool_ops->get_dump_flag)
+ if (!ops->get_dump_flag)
return -EOPNOTSUPP;
if (copy_from_user(&dump, useraddr, sizeof(dump)))
@@ -1299,8 +1301,7 @@ static int ethtool_get_dump_data(struct net_device *dev,
const struct ethtool_ops *ops = dev->ethtool_ops;
void *data = NULL;
- if (!dev->ethtool_ops->get_dump_data ||
- !dev->ethtool_ops->get_dump_flag)
+ if (!ops->get_dump_data || !ops->get_dump_flag)
return -EOPNOTSUPP;
if (copy_from_user(&dump, useraddr, sizeof(dump)))
@@ -1346,13 +1347,9 @@ static int ethtool_get_ts_info(struct net_device *dev, void __user *useraddr)
info.cmd = ETHTOOL_GET_TS_INFO;
if (phydev && phydev->drv && phydev->drv->ts_info) {
-
err = phydev->drv->ts_info(phydev, &info);
-
- } else if (dev->ethtool_ops && dev->ethtool_ops->get_ts_info) {
-
+ } else if (ops->get_ts_info) {
err = ops->get_ts_info(dev, &info);
-
} else {
info.so_timestamping =
SOF_TIMESTAMPING_RX_SOFTWARE |
--
1.8.1
^ permalink raw reply related
* Re: [PATCH 2/2] ipv6: fix packet corruption when Dest/RT2 options are used
From: Steffen Klassert @ 2013-01-07 12:41 UTC (permalink / raw)
To: Nicolas Dichtel; +Cc: Romain KUNTZ, netdev, yoshfuji, davem
In-Reply-To: <50EAA84F.90408@6wind.com>
On Mon, Jan 07, 2013 at 11:49:51AM +0100, Nicolas Dichtel wrote:
> Le 05/01/2013 17:19, Romain KUNTZ a écrit :
> >Commit 299b0767 (ipv6: Fix IPsec slowpath fragmentation problem)
> Add Steffen into CC, he is the author of this patch and the IPsec
> maintainer.
>
> >has introduced a bug that provokes corrupted packets when Destination
> >Options or Routing Header Type 2 are used (such as with Mobile IPv6):
> >rt->rt6i_nfheader_len should be substracted to rt->dst.header_len,
> >and not to exthdrlen.
I had no Mobile IPv6 test case, so I likely overlooked this.
> >
> >This patch reverts to the original and correct behavior. Successfully
> >tested with and without IPsec activated for MH packets.
> >
> >Signed-off-by: Romain Kuntz <r.kuntz@ipflavors.com>
Thanks for catching!
Acked-by: Steffen Klassert <steffen.klassert@secunet.com>
^ permalink raw reply
* Re: [PATCH net-next] xfrm: removes a superfluous check and add a statistic
From: Steffen Klassert @ 2013-01-07 12:51 UTC (permalink / raw)
To: roy.qing.li; +Cc: netdev
In-Reply-To: <1356681988-7985-1-git-send-email-roy.qing.li@gmail.com>
On Fri, Dec 28, 2012 at 04:06:28PM +0800, roy.qing.li@gmail.com wrote:
> From: Li RongQing <roy.qing.li@gmail.com>
>
> Remove the check if x->km.state equal to XFRM_STATE_VALID in
> xfrm_state_check_expire(), which will be done before call
> xfrm_state_check_expire().
>
> add a LINUX_MIB_XFRMOUTSTATEINVALID statistic to record the
> outbound error due to invalid xfrm state.
>
> Signed-off-by: Li RongQing <roy.qing.li@gmail.com>
Applied to ipsec-next,
Thanks!
^ permalink raw reply
* Re: [RFC PATCH] ah4/esp4: set transport header correctly for IPsec tunnel mode.
From: Steffen Klassert @ 2013-01-07 13:00 UTC (permalink / raw)
To: roy.qing.li; +Cc: netdev
In-Reply-To: <1356682036-25642-1-git-send-email-roy.qing.li@gmail.com>
On Fri, Dec 28, 2012 at 04:07:16PM +0800, roy.qing.li@gmail.com wrote:
> From: Li RongQing <roy.qing.li@gmail.com>
>
> IPsec tunnel does not set ECN field to CE in inner header when
> the ECN field in the outer header is CE, and the ECN field in
> the inner header is ECT(0) or ECT(1).
>
> The cause is ipip_hdr() does not return the correct address of
> inner header since skb->transport-header is not the inner header
> after esp_input_done2(), or ah_input().
>
> Signed-off-by: Li RongQing <roy.qing.li@gmail.com>
> ---
> I know this bug, but no lab to verify if my patch is correct,
> hope netdev experts can inspect this patch carefully, if this
> can be accepted, I will do same fix for ah6/esp6
This looks ok to me, please submit the ipv6 side too.
Thanks!
^ permalink raw reply
* Re: [PATCH v2] sctp: Change defaults on cookie hmac selection
From: Florian Fainelli @ 2013-01-07 13:25 UTC (permalink / raw)
To: Neil Horman
Cc: netdev, David Miller, Linus Torvalds, Vlad Yasevich, linux-sctp
In-Reply-To: <1355534521-32719-1-git-send-email-nhorman@tuxdriver.com>
Hello Neil,
Le 12/15/12 02:22, Neil Horman a écrit :
> Recently I posted commit 3c68198e75 which made selection of the cookie hmac
> algorithm selectable. This is all well and good, but Linus noted that it
> changes the default config:
> http://marc.info/?l=linux-netdev&m=135536629004808&w=2
>
> I've modified the sctp Kconfig file to reflect the recommended way of making
> this choice, using the thermal driver example specified, and brought the
> defaults back into line with the way they were prior to my origional patch
>
> Also, on Linus' suggestion, re-adding ability to select default 'none' hmac
> algorithm, so we don't needlessly bloat the kernel by forcing a non-none
> default. This also led me to note that we won't honor the default none
> condition properly because of how sctp_net_init is encoded. Fix that up as
> well.
>
> Tested by myself (allbeit fairly quickly). All configuration combinations seems
> to work soundly.
>
> Signed-off-by: Neil Horman <nhorman@tuxdriver.com>
> CC: David Miller <davem@davemloft.net>
> CC: Linus Torvalds <torvalds@linux-foundation.org>
> CC: Vlad Yasevich <vyasevich@gmail.com>
> CC: linux-sctp@vger.kernel.org
> ---
> net/sctp/Kconfig | 27 +++++++++++++++++++++++++--
> net/sctp/protocol.c | 4 ++--
> 2 files changed, 27 insertions(+), 4 deletions(-)
>
> diff --git a/net/sctp/Kconfig b/net/sctp/Kconfig
> index a9edd2e..c262106 100644
> --- a/net/sctp/Kconfig
> +++ b/net/sctp/Kconfig
> @@ -66,12 +66,36 @@ config SCTP_DBG_OBJCNT
> 'cat /proc/net/sctp/sctp_dbg_objcnt'
>
> If unsure, say N
> +choice
> + prompt "Default SCTP cookie HMAC encoding"
> + default SCTP_COOKIE_HMAC_MD5
Should not this be SCTP_DEFAULT_COOKIE_HMAC_MD5? I just tried to update
to 3.8-rc2, and I usually build my kernel-headers with:
yes '' | ARCH=foo make oldconfig
and this just kept asking me for this config symbol because none could
be provided.
--
Florian
^ permalink raw reply
* Re: [PATCH] xen/netfront: improve truesize tracking
From: Ian Campbell @ 2013-01-07 13:41 UTC (permalink / raw)
To: Sander Eikelenboom
Cc: Rick Jones, Eric Dumazet, netdev@vger.kernel.org,
Konrad Rzeszutek Wilk, annie li, xen-devel@lists.xensource.com
In-Reply-To: <561084196.20130103214030@eikelenboom.it>
On Thu, 2013-01-03 at 20:40 +0000, Sander Eikelenboom wrote:
> Friday, December 21, 2012, 7:33:43 PM, you wrote:
>
> > I'm guessing that trusize checks matter more on the "inbound" path than
> > the outbound path? If that is indeed the case, then instead of, or in
> > addition to using the -s option to set the local (netperf side) socket
> > buffer size, you should use a -S option to set the remote (netserver
> > side) socket buffer size.
>
> > happy benchmarking,
>
> > rick jones
>
>
> OK, ran them with -S as well:
Are these all from domU -> dom0 ? Did you try traffic going the other
way?
> "current" is with netfront as is (skb->truesize += skb->data_len - RX_COPY_THRESHOLD;)
> "patched" is with IanC's latest patch (skb->truesize += PAGE_SIZE * skb_shinfo(skb)->nr_frags;)
skb->truesize += skb->data_len - NETFRONT_SKB_CB(skb)->pull_to; is
probably more interesting to compare against since we know the current
one is buggy.
These number generally look good, largely +/- 1%, often in favour of the
updated code but these two stand out as worrying:
> TCP STREAM TEST from 0.0.0.0 (0.0.0.0) port 0 AF_INET to 192.168.1.1 (192.168.1.1) port 0 AF_INET : +/-2.500% @ 95% conf. : demo
> Recv Send Send
> Socket Socket Message Elapsed
> Size Size Size Time Throughput
> bytes bytes bytes secs. KBytes/sec
>
> current 18000 16384 1432 60.00 37559.94
> patched 18000 16384 1432 60.00 40630.66
>
> TCP STREAM TEST from 0.0.0.0 (0.0.0.0) port 0 AF_INET to 192.168.1.1 (192.168.1.1) port 0 AF_INET : +/-2.500% @ 95% conf. : demo
> Recv Send Send
> Socket Socket Message Elapsed
> Size Size Size Time Throughput
> bytes bytes bytes secs. KBytes/sec
>
> current 28000 16384 16384 60.00 103766.68
> patched 28000 16384 16384 60.00 93277.98
That's at least a 10% slow down in both cases.
> UDP UNIDIRECTIONAL SEND TEST from 0.0.0.0 (0.0.0.0) port 0 AF_INET to 192.168.1.1 (192.168.1.1) port 0 AF_INET : +/-2.500% @ 95% conf. : demo
> Socket Message Elapsed Messages
> Size Size Time Okay Errors Throughput
> bytes bytes secs # # KBytes/sec
>
> current 212992 65507 60.00 252586 0 269305.73
> current 2280 60.00 229371 244553.96
> patched 212992 65507 60.00 256209 0 273168.32
> patched 2280 60.00 201670 215019.54
The recv numbers here aren't too pleasing either.
However, given that this fixes a real issue which people are seeing I'd
be inclined to go with it, at least for now.
Ian.
^ permalink raw reply
* Re: [PATCH] xen/netfront: improve truesize tracking
From: Sander Eikelenboom @ 2013-01-07 14:11 UTC (permalink / raw)
To: Ian Campbell
Cc: Rick Jones, Eric Dumazet, netdev@vger.kernel.org,
Konrad Rzeszutek Wilk, annie li, xen-devel@lists.xensource.com
In-Reply-To: <1357566063.7989.68.camel@zakaz.uk.xensource.com>
Monday, January 7, 2013, 2:41:03 PM, you wrote:
> On Thu, 2013-01-03 at 20:40 +0000, Sander Eikelenboom wrote:
>> Friday, December 21, 2012, 7:33:43 PM, you wrote:
>>
>> > I'm guessing that trusize checks matter more on the "inbound" path than
>> > the outbound path? If that is indeed the case, then instead of, or in
>> > addition to using the -s option to set the local (netperf side) socket
>> > buffer size, you should use a -S option to set the remote (netserver
>> > side) socket buffer size.
>>
>> > happy benchmarking,
>>
>> > rick jones
>>
>>
>> OK, ran them with -S as well:
> Are these all from domU -> dom0 ? Did you try traffic going the other
> way?
Yes running netperf in domU and netserver in dom0, but i must say i'm far from a netperf expert.
So i don't even know for sure if the tests i ran give a good picture.
>> "current" is with netfront as is (skb->truesize += skb->data_len - RX_COPY_THRESHOLD;)
>> "patched" is with IanC's latest patch (skb->truesize += PAGE_SIZE * skb_shinfo(skb)->nr_frags;)
skb->>truesize += skb->data_len - NETFRONT_SKB_CB(skb)->pull_to; is
> probably more interesting to compare against since we know the current
> one is buggy.
Will see if i can run against that as well, although i thought Eric said to prefer the "skb->truesize += PAGE_SIZE * skb_shinfo(skb)->nr_frags;"
> These number generally look good, largely +/- 1%, often in favour of the
> updated code but these two stand out as worrying:
>> TCP STREAM TEST from 0.0.0.0 (0.0.0.0) port 0 AF_INET to 192.168.1.1 (192.168.1.1) port 0 AF_INET : +/-2.500% @ 95% conf. : demo
>> Recv Send Send
>> Socket Socket Message Elapsed
>> Size Size Size Time Throughput
>> bytes bytes bytes secs. KBytes/sec
>>
>> current 18000 16384 1432 60.00 37559.94
>> patched 18000 16384 1432 60.00 40630.66
>>
>> TCP STREAM TEST from 0.0.0.0 (0.0.0.0) port 0 AF_INET to 192.168.1.1 (192.168.1.1) port 0 AF_INET : +/-2.500% @ 95% conf. : demo
>> Recv Send Send
>> Socket Socket Message Elapsed
>> Size Size Size Time Throughput
>> bytes bytes bytes secs. KBytes/sec
>>
>> current 28000 16384 16384 60.00 103766.68
>> patched 28000 16384 16384 60.00 93277.98
> That's at least a 10% slow down in both cases.
>> UDP UNIDIRECTIONAL SEND TEST from 0.0.0.0 (0.0.0.0) port 0 AF_INET to 192.168.1.1 (192.168.1.1) port 0 AF_INET : +/-2.500% @ 95% conf. : demo
>> Socket Message Elapsed Messages
>> Size Size Time Okay Errors Throughput
>> bytes bytes secs # # KBytes/sec
>>
>> current 212992 65507 60.00 252586 0 269305.73
>> current 2280 60.00 229371 244553.96
>> patched 212992 65507 60.00 256209 0 273168.32
>> patched 2280 60.00 201670 215019.54
> The recv numbers here aren't too pleasing either.
> However, given that this fixes a real issue which people are seeing I'd
> be inclined to go with it, at least for now.
> Ian.
^ permalink raw reply
* Re: [PATCH 4/4 v3] net/smsc911x: Provide common clock functionality
From: Lee Jones @ 2013-01-07 14:16 UTC (permalink / raw)
To: Linus Walleij
Cc: Russell King - ARM Linux, Steve Glendinning, Robert Marklund,
linus.walleij, arnd, netdev, linux-kernel, linux-arm-kernel
In-Reply-To: <CACRpkda-4C+ezaZFSkxsNbmHnBN8RCoCeGePaOF-DzV0XnkzQw@mail.gmail.com>
On Thu, 03 Jan 2013, Linus Walleij wrote:
> On Thu, Jan 3, 2013 at 12:14 PM, Lee Jones <lee.jones@linaro.org> wrote:
>
> > Some platforms provide clocks which require enabling before the
> > SMSC911x chip will power on. This patch uses the new common clk
> > framework to do just that. If no clock is provided, it will just
> > be ignored and the driver will continue to assume that no clock
> > is required for the chip to run successfully.
> >
> > Cc: Steve Glendinning <steve.glendinning@shawell.net>
> > Cc: netdev@vger.kernel.org
> > Signed-off-by: Lee Jones <lee.jones@linaro.org>
>
> Looks all right to me now:
> Reviewed-by: Linus Walleij <linus.walleij@linaro.org>
Great, thanks Linus.
Who will take this patch now?
--
Lee Jones
Linaro ST-Ericsson Landing Team Lead
Linaro.org │ Open source software for ARM SoCs
Follow Linaro: Facebook | Twitter | Blog
^ permalink raw reply
* Re: [PATCH] xen/netfront: improve truesize tracking
From: Ian Campbell @ 2013-01-07 14:22 UTC (permalink / raw)
To: Sander Eikelenboom
Cc: Rick Jones, Eric Dumazet, netdev@vger.kernel.org,
Konrad Rzeszutek Wilk, annie li, xen-devel@lists.xensource.com
In-Reply-To: <606842712.20130107151133@eikelenboom.it>
On Mon, 2013-01-07 at 14:11 +0000, Sander Eikelenboom wrote:
> Monday, January 7, 2013, 2:41:03 PM, you wrote:
>
> > On Thu, 2013-01-03 at 20:40 +0000, Sander Eikelenboom wrote:
> >> Friday, December 21, 2012, 7:33:43 PM, you wrote:
> >>
> >> > I'm guessing that trusize checks matter more on the "inbound" path than
> >> > the outbound path? If that is indeed the case, then instead of, or in
> >> > addition to using the -s option to set the local (netperf side) socket
> >> > buffer size, you should use a -S option to set the remote (netserver
> >> > side) socket buffer size.
> >>
> >> > happy benchmarking,
> >>
> >> > rick jones
> >>
> >>
> >> OK, ran them with -S as well:
>
> > Are these all from domU -> dom0 ? Did you try traffic going the other
> > way?
>
> Yes running netperf in domU and netserver in dom0, but i must say i'm far from a netperf expert.
> So i don't even know for sure if the tests i ran give a good picture.
>
> >> "current" is with netfront as is (skb->truesize += skb->data_len - RX_COPY_THRESHOLD;)
> >> "patched" is with IanC's latest patch (skb->truesize += PAGE_SIZE * skb_shinfo(skb)->nr_frags;)
>
> skb->>truesize += skb->data_len - NETFRONT_SKB_CB(skb)->pull_to; is
> > probably more interesting to compare against since we know the current
> > one is buggy.
>
> Will see if i can run against that as well, although i thought Eric
> said to prefer the "skb->truesize += PAGE_SIZE *
> skb_shinfo(skb)->nr_frags;"
Right, I meant to compare "PAGE_SIZE * skb_shinfo(skb)->nr_frags" vs
"skb->data_len - NETFRONT_SKB_CB(skb)->pull_to". TBH I trust Eric so I'm
inclined to just go with what he suggests.
Ian.
^ permalink raw reply
* Re: [PATCH v2] sctp: Change defaults on cookie hmac selection
From: Neil Horman @ 2013-01-07 14:49 UTC (permalink / raw)
To: Florian Fainelli
Cc: netdev, David Miller, Linus Torvalds, Vlad Yasevich, linux-sctp
In-Reply-To: <50EACCD3.90609@openwrt.org>
On Mon, Jan 07, 2013 at 02:25:39PM +0100, Florian Fainelli wrote:
> Hello Neil,
>
> Le 12/15/12 02:22, Neil Horman a écrit :
> >Recently I posted commit 3c68198e75 which made selection of the cookie hmac
> >algorithm selectable. This is all well and good, but Linus noted that it
> >changes the default config:
> >http://marc.info/?l=linux-netdev&m=135536629004808&w=2
> >
> >I've modified the sctp Kconfig file to reflect the recommended way of making
> >this choice, using the thermal driver example specified, and brought the
> >defaults back into line with the way they were prior to my origional patch
> >
> >Also, on Linus' suggestion, re-adding ability to select default 'none' hmac
> >algorithm, so we don't needlessly bloat the kernel by forcing a non-none
> >default. This also led me to note that we won't honor the default none
> >condition properly because of how sctp_net_init is encoded. Fix that up as
> >well.
> >
> >Tested by myself (allbeit fairly quickly). All configuration combinations seems
> >to work soundly.
> >
> >Signed-off-by: Neil Horman <nhorman@tuxdriver.com>
> >CC: David Miller <davem@davemloft.net>
> >CC: Linus Torvalds <torvalds@linux-foundation.org>
> >CC: Vlad Yasevich <vyasevich@gmail.com>
> >CC: linux-sctp@vger.kernel.org
> >---
> > net/sctp/Kconfig | 27 +++++++++++++++++++++++++--
> > net/sctp/protocol.c | 4 ++--
> > 2 files changed, 27 insertions(+), 4 deletions(-)
> >
> >diff --git a/net/sctp/Kconfig b/net/sctp/Kconfig
> >index a9edd2e..c262106 100644
> >--- a/net/sctp/Kconfig
> >+++ b/net/sctp/Kconfig
> >@@ -66,12 +66,36 @@ config SCTP_DBG_OBJCNT
> > 'cat /proc/net/sctp/sctp_dbg_objcnt'
> >
> > If unsure, say N
> >+choice
> >+ prompt "Default SCTP cookie HMAC encoding"
> >+ default SCTP_COOKIE_HMAC_MD5
>
> Should not this be SCTP_DEFAULT_COOKIE_HMAC_MD5? I just tried to
> update to 3.8-rc2, and I usually build my kernel-headers with:
>
> yes '' | ARCH=foo make oldconfig
>
> and this just kept asking me for this config symbol because none
> could be provided.
> --
> Florian
>
No, the config mechanism is setup to offer the user the ability to choose a
default cookie hmac, alg, then optionally select any other hmac algs you would
like to be made available (in the event you want to change the default at run
time). When you select the default, it eables (via the select directive), the
corresponding SCTP_COOKIE_HMAC_* config option, which is used in the build, and
then prompts for the remaining values.
Neil
^ permalink raw reply
* Re: [PATCH V3 2/2] vhost: handle polling errors
From: Michael S. Tsirkin @ 2013-01-07 14:55 UTC (permalink / raw)
To: Jason Wang; +Cc: kvm, eric.dumazet, netdev, linux-kernel, virtualization, davem
In-Reply-To: <50EA5139.7000904@redhat.com>
On Mon, Jan 07, 2013 at 12:38:17PM +0800, Jason Wang wrote:
> On 01/06/2013 09:22 PM, Michael S. Tsirkin wrote:
> > On Sun, Jan 06, 2013 at 03:18:38PM +0800, Jason Wang wrote:
> >> Polling errors were ignored by vhost/vhost_net, this may lead to crash when
> >> trying to remove vhost from waitqueue when after the polling is failed. Solve
> >> this problem by:
> >>
> >> - checking the poll->wqh before trying to remove from waitqueue
> >> - report an error when poll() returns a POLLERR in vhost_start_poll()
> >> - report an error when vhost_start_poll() fails in
> >> vhost_vring_ioctl()/vhost_net_set_backend() which is used to notify the
> >> failure to userspace.
> >> - report an error in the data path in vhost_net when meet polling errors.
> >>
> >> After those changes, we can safely drop the tx polling state in vhost_net since
> >> it was replaced by the checking of poll->wqh.
> >>
> >> Signed-off-by: Jason Wang <jasowang@redhat.com>
> >> ---
> >> drivers/vhost/net.c | 74 ++++++++++++++++--------------------------------
> >> drivers/vhost/vhost.c | 31 +++++++++++++++-----
> >> drivers/vhost/vhost.h | 2 +-
> >> 3 files changed, 49 insertions(+), 58 deletions(-)
> >>
> >> diff --git a/drivers/vhost/net.c b/drivers/vhost/net.c
> >> index d10ad6f..125c1e5 100644
> >> --- a/drivers/vhost/net.c
> >> +++ b/drivers/vhost/net.c
> >> @@ -64,20 +64,10 @@ enum {
> >> VHOST_NET_VQ_MAX = 2,
> >> };
> >>
> >> -enum vhost_net_poll_state {
> >> - VHOST_NET_POLL_DISABLED = 0,
> >> - VHOST_NET_POLL_STARTED = 1,
> >> - VHOST_NET_POLL_STOPPED = 2,
> >> -};
> >> -
> >> struct vhost_net {
> >> struct vhost_dev dev;
> >> struct vhost_virtqueue vqs[VHOST_NET_VQ_MAX];
> >> struct vhost_poll poll[VHOST_NET_VQ_MAX];
> >> - /* Tells us whether we are polling a socket for TX.
> >> - * We only do this when socket buffer fills up.
> >> - * Protected by tx vq lock. */
> >> - enum vhost_net_poll_state tx_poll_state;
> >> /* Number of TX recently submitted.
> >> * Protected by tx vq lock. */
> >> unsigned tx_packets;
> >> @@ -155,24 +145,6 @@ static void copy_iovec_hdr(const struct iovec *from, struct iovec *to,
> >> }
> >> }
> >>
> >> -/* Caller must have TX VQ lock */
> >> -static void tx_poll_stop(struct vhost_net *net)
> >> -{
> >> - if (likely(net->tx_poll_state != VHOST_NET_POLL_STARTED))
> >> - return;
> >> - vhost_poll_stop(net->poll + VHOST_NET_VQ_TX);
> >> - net->tx_poll_state = VHOST_NET_POLL_STOPPED;
> >> -}
> >> -
> >> -/* Caller must have TX VQ lock */
> >> -static void tx_poll_start(struct vhost_net *net, struct socket *sock)
> >> -{
> >> - if (unlikely(net->tx_poll_state != VHOST_NET_POLL_STOPPED))
> >> - return;
> >> - vhost_poll_start(net->poll + VHOST_NET_VQ_TX, sock->file);
> >> - net->tx_poll_state = VHOST_NET_POLL_STARTED;
> >> -}
> >> -
> >> /* In case of DMA done not in order in lower device driver for some reason.
> >> * upend_idx is used to track end of used idx, done_idx is used to track head
> >> * of used idx. Once lower device DMA done contiguously, we will signal KVM
> >> @@ -227,6 +199,7 @@ static void vhost_zerocopy_callback(struct ubuf_info *ubuf, bool success)
> >> static void handle_tx(struct vhost_net *net)
> >> {
> >> struct vhost_virtqueue *vq = &net->dev.vqs[VHOST_NET_VQ_TX];
> >> + struct vhost_poll *poll = net->poll + VHOST_NET_VQ_TX;
> >> unsigned out, in, s;
> >> int head;
> >> struct msghdr msg = {
> >> @@ -252,7 +225,8 @@ static void handle_tx(struct vhost_net *net)
> >> wmem = atomic_read(&sock->sk->sk_wmem_alloc);
> >> if (wmem >= sock->sk->sk_sndbuf) {
> >> mutex_lock(&vq->mutex);
> >> - tx_poll_start(net, sock);
> >> + if (vhost_poll_start(poll, sock->file))
> >> + vq_err(vq, "Fail to start TX polling\n");
> > s/Fail/Failed/
> >
> > A question though: how can this happen? Could you clarify please?
> > Maybe we can find a way to prevent this error?
>
> Two conditions I think this can happen:
>
> 1) a buggy userspace disable a queue through TUNSETQUEUE
> 2) the net device were gone
>
> For 1, looks like we can delay the disabling until the refcnt goes to
> zero. For 2 may needs more changes.
I'd expect keeping a socket reference would prevent both issues.
Doesn't it?
> Not sure it's worth to do this work,
> maybe a warning is enough just like other failure.
With other failures, you normally can correct the error then
kick to have it restart. This is soomething thagt would not
work here.
> >
> >> mutex_unlock(&vq->mutex);
> >> return;
> >> }
> >> @@ -261,7 +235,7 @@ static void handle_tx(struct vhost_net *net)
> >> vhost_disable_notify(&net->dev, vq);
> >>
> >> if (wmem < sock->sk->sk_sndbuf / 2)
> >> - tx_poll_stop(net);
> >> + vhost_poll_stop(poll);
> >> hdr_size = vq->vhost_hlen;
> >> zcopy = vq->ubufs;
> >>
> >> @@ -283,8 +257,10 @@ static void handle_tx(struct vhost_net *net)
> >>
> >> wmem = atomic_read(&sock->sk->sk_wmem_alloc);
> >> if (wmem >= sock->sk->sk_sndbuf * 3 / 4) {
> >> - tx_poll_start(net, sock);
> >> - set_bit(SOCK_ASYNC_NOSPACE, &sock->flags);
> >> + if (vhost_poll_start(poll, sock->file))
> >> + vq_err(vq, "Fail to start TX polling\n");
> >> + else
> >> + set_bit(SOCK_ASYNC_NOSPACE, &sock->flags);
> >> break;
> >> }
> >> /* If more outstanding DMAs, queue the work.
> >> @@ -294,8 +270,10 @@ static void handle_tx(struct vhost_net *net)
> >> (vq->upend_idx - vq->done_idx) :
> >> (vq->upend_idx + UIO_MAXIOV - vq->done_idx);
> >> if (unlikely(num_pends > VHOST_MAX_PEND)) {
> >> - tx_poll_start(net, sock);
> >> - set_bit(SOCK_ASYNC_NOSPACE, &sock->flags);
> >> + if (vhost_poll_start(poll, sock->file))
> >> + vq_err(vq, "Fail to start TX polling\n");
> >> + else
> >> + set_bit(SOCK_ASYNC_NOSPACE, &sock->flags);
> >> break;
> >> }
> >> if (unlikely(vhost_enable_notify(&net->dev, vq))) {
> >> @@ -360,7 +338,8 @@ static void handle_tx(struct vhost_net *net)
> >> }
> >> vhost_discard_vq_desc(vq, 1);
> >> if (err == -EAGAIN || err == -ENOBUFS)
> >> - tx_poll_start(net, sock);
> >> + if (vhost_poll_start(poll, sock->file))
> >> + vq_err(vq, "Fail to start TX polling\n");
> >> break;
> >> }
> >> if (err != len)
> >> @@ -623,7 +602,6 @@ static int vhost_net_open(struct inode *inode, struct file *f)
> >>
> >> vhost_poll_init(n->poll + VHOST_NET_VQ_TX, handle_tx_net, POLLOUT, dev);
> >> vhost_poll_init(n->poll + VHOST_NET_VQ_RX, handle_rx_net, POLLIN, dev);
> >> - n->tx_poll_state = VHOST_NET_POLL_DISABLED;
> >>
> >> f->private_data = n;
> >>
> >> @@ -633,29 +611,25 @@ static int vhost_net_open(struct inode *inode, struct file *f)
> >> static void vhost_net_disable_vq(struct vhost_net *n,
> >> struct vhost_virtqueue *vq)
> >> {
> >> + struct vhost_poll *poll = n->poll + (vq - n->vqs);
> >> +
> >> if (!vq->private_data)
> >> return;
> >> - if (vq == n->vqs + VHOST_NET_VQ_TX) {
> >> - tx_poll_stop(n);
> >> - n->tx_poll_state = VHOST_NET_POLL_DISABLED;
> >> - } else
> >> - vhost_poll_stop(n->poll + VHOST_NET_VQ_RX);
> >> + vhost_poll_stop(poll);
> >> }
> >>
> >> -static void vhost_net_enable_vq(struct vhost_net *n,
> >> +static int vhost_net_enable_vq(struct vhost_net *n,
> >> struct vhost_virtqueue *vq)
> >> {
> >> struct socket *sock;
> >> + struct vhost_poll *poll = n->poll + (vq - n->vqs);
> >>
> >> sock = rcu_dereference_protected(vq->private_data,
> >> lockdep_is_held(&vq->mutex));
> >> if (!sock)
> >> - return;
> >> - if (vq == n->vqs + VHOST_NET_VQ_TX) {
> >> - n->tx_poll_state = VHOST_NET_POLL_STOPPED;
> >> - tx_poll_start(n, sock);
> >> - } else
> >> - vhost_poll_start(n->poll + VHOST_NET_VQ_RX, sock->file);
> >> + return 0;
> >> +
> >> + return vhost_poll_start(poll, sock->file);
> >> }
> >>
> >> static struct socket *vhost_net_stop_vq(struct vhost_net *n,
> >> @@ -833,7 +807,9 @@ static long vhost_net_set_backend(struct vhost_net *n, unsigned index, int fd)
> >> r = vhost_init_used(vq);
> >> if (r)
> >> goto err_used;
> >> - vhost_net_enable_vq(n, vq);
> >> + r = vhost_net_enable_vq(n, vq);
> >> + if (r)
> >> + goto err_used;
> >>
> >> oldubufs = vq->ubufs;
> >> vq->ubufs = ubufs;
> >> diff --git a/drivers/vhost/vhost.c b/drivers/vhost/vhost.c
> >> index 34389f7..5c7a466 100644
> >> --- a/drivers/vhost/vhost.c
> >> +++ b/drivers/vhost/vhost.c
> >> @@ -77,26 +77,41 @@ void vhost_poll_init(struct vhost_poll *poll, vhost_work_fn_t fn,
> >> init_poll_funcptr(&poll->table, vhost_poll_func);
> >> poll->mask = mask;
> >> poll->dev = dev;
> >> + poll->wqh = NULL;
> >>
> >> vhost_work_init(&poll->work, fn);
> >> }
> >>
> >> +/* Stop polling a file. After this function returns, it becomes safe to drop the
> >> + * file reference. You must also flush afterwards. */
> >> +void vhost_poll_stop(struct vhost_poll *poll)
> >> +{
> >> + if (poll->wqh) {
> >> + remove_wait_queue(poll->wqh, &poll->wait);
> >> + poll->wqh = NULL;
> >> + }
> >> +}
> >> +
> >> /* Start polling a file. We add ourselves to file's wait queue. The caller must
> >> * keep a reference to a file until after vhost_poll_stop is called. */
> >> -void vhost_poll_start(struct vhost_poll *poll, struct file *file)
> >> +int vhost_poll_start(struct vhost_poll *poll, struct file *file)
> >> {
> >> unsigned long mask;
> >> + int ret = 0;
> >> +
> >> + if (poll->wqh)
> >> + return -EBUSY;
> >>
> > I think this should return success: we are already polling.
> > Otherwise this would trigger a bug below I think.
>
> Ok.
> >
> >> mask = file->f_op->poll(file, &poll->table);
> >> if (mask)
> >> vhost_poll_wakeup(&poll->wait, 0, 0, (void *)mask);
> >> -}
> >>
> >> -/* Stop polling a file. After this function returns, it becomes safe to drop the
> >> - * file reference. You must also flush afterwards. */
> >> -void vhost_poll_stop(struct vhost_poll *poll)
> >> -{
> >> - remove_wait_queue(poll->wqh, &poll->wait);
> >> + if (mask & POLLERR) {
> >> + ret = -EINVAL;
> >> + vhost_poll_stop(poll);
> >> + }
> >> +
> >> + return ret;
> >> }
> >>
> >> static bool vhost_work_seq_done(struct vhost_dev *dev, struct vhost_work *work,
> >> @@ -792,7 +807,7 @@ long vhost_vring_ioctl(struct vhost_dev *d, int ioctl, void __user *argp)
> >> fput(filep);
> >>
> >> if (pollstart && vq->handle_kick)
> >> - vhost_poll_start(&vq->poll, vq->kick);
> >> + r = vhost_poll_start(&vq->poll, vq->kick);
> >>
> >> mutex_unlock(&vq->mutex);
> >>
> >> diff --git a/drivers/vhost/vhost.h b/drivers/vhost/vhost.h
> >> index 2639c58..17261e2 100644
> >> --- a/drivers/vhost/vhost.h
> >> +++ b/drivers/vhost/vhost.h
> >> @@ -42,7 +42,7 @@ void vhost_work_queue(struct vhost_dev *dev, struct vhost_work *work);
> >>
> >> void vhost_poll_init(struct vhost_poll *poll, vhost_work_fn_t fn,
> >> unsigned long mask, struct vhost_dev *dev);
> >> -void vhost_poll_start(struct vhost_poll *poll, struct file *file);
> >> +int vhost_poll_start(struct vhost_poll *poll, struct file *file);
> >> void vhost_poll_stop(struct vhost_poll *poll);
> >> void vhost_poll_flush(struct vhost_poll *poll);
> >> void vhost_poll_queue(struct vhost_poll *poll);
> >> --
> >> 1.7.1
> > --
> > To unsubscribe from this list: send the line "unsubscribe netdev" in
> > the body of a message to majordomo@vger.kernel.org
> > More majordomo info at http://vger.kernel.org/majordomo-info.html
^ permalink raw reply
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox