* Re: [Patch net-next] net_sched: call qdisc_reset() with qdisc lock
From: John Fastabend @ 2017-12-22 3:36 UTC (permalink / raw)
To: Cong Wang, netdev; +Cc: jakub.kicinski
In-Reply-To: <20171222000330.29009-1-xiyou.wangcong@gmail.com>
On 12/21/2017 04:03 PM, Cong Wang wrote:
> qdisc_reset() should always be called with qdisc spinlock
> and with BH disabled, otherwise qdisc ->reset() could race
> with TX BH.
>
hmm I don't see how this fixes the issue. pfifo_fast is no longer
using the qdisc lock so that doesn't help. And it is only a
local_bh_disable.
> Fixes: 7bbde83b1860 ("net: sched: drop qdisc_reset from dev_graft_qdisc")
> Reported-by: Jakub Kicinski <jakub.kicinski@netronome.com>
> Cc: John Fastabend <john.fastabend@gmail.com>
> Signed-off-by: Cong Wang <xiyou.wangcong@gmail.com>
> ---
> net/sched/sch_generic.c | 5 ++++-
> 1 file changed, 4 insertions(+), 1 deletion(-)
>
> diff --git a/net/sched/sch_generic.c b/net/sched/sch_generic.c
> index 10aaa3b615ce..00ddb5f8f430 100644
> --- a/net/sched/sch_generic.c
> +++ b/net/sched/sch_generic.c
> @@ -1097,8 +1097,11 @@ static void dev_qdisc_reset(struct net_device *dev,
> {
> struct Qdisc *qdisc = dev_queue->qdisc_sleeping;
>
> - if (qdisc)
> + if (qdisc) {
> + spin_lock_bh(qdisc_lock(qdisc));
> qdisc_reset(qdisc);
> + spin_unlock_bh(qdisc_lock(qdisc));
> + }
> }
>
> /**
>
OK first the cases to get to qdisc_reset that I've tracked
down are,
dev_shutdown()
qdisc_destroy()
dev_deactivate_many()
dev_qdisc_reset() <- for each txq
qdisc_reset()
chained calls from qdisc_reset ops
At the moment all the lockless qdiscs don't care about chained
calls so we can ignore that, but would be nice to keep in mind.
Next qdisc_reset() is doing a couple things calling the qdisc
ops reset call but also walking gso_skb and skb_bad_txq. The
'unlink' operations there are not safe to be called while an
enqueue/dequeue op is in-flight. Also pfifo_fast's reset op
is not safe to be called with enqueue/dequeue ops in-flight.
So I've made the assumption that qdisc_reset is _only_ ever
called after a qdisc is no longer attached on the enqueue
dev_xmit side and also any in-progress tx_action calls are
completed. For what its worth this has always been the assumption
AFAIK.
So those are the assumptions what did I miss?
The biggest gap I see is dev_deactivate_many() is supposed
to wait for all tx_action calls to complete, this bit:
/* Wait for outstanding qdisc_run calls. */
list_for_each_entry(dev, head, close_list) {
while (some_qdisc_is_busy(dev))
yield();
Where some_qdisc_is_busy in the lockless case only does
the following,
if (q->flags & TCQ_F_NOLOCK) {
val = test_bit(__QDISC_STATE_SCHED, &q->state);
Oops that only tells us something is scheduled nothing about
if something is running. Excerpt from tx_action side here
clear_bit(__QDISC_STATE_SCHED, &q->state);
qdisc_run(q);
For comparison here is the check in the qdisc locked branch of
some_qdisc_is_busy,
root_lock = qdisc_lock(q);
spin_lock_bh(root_lock);
val = (qdisc_is_running(q) ||
test_bit(__QDISC_STATE_SCHED, &q->state));
spin_unlock_bh(root_lock);
previously we had the qdisc_lock() to protect the bit clear and then in
the some_qdisc_is_busy case we still did a qdisc_is_running() call. The
easiest fix I see is add the qdisc_is_running() check to the TCQ_F_NOLOCK
case in some_qdisc_is_busy AND to be correct I guess we should set the
running bit before clearing the QDISC_STATE_SCHED bit to be correct.
Untested but perhaps as simple as,
diff --git a/net/sched/sch_generic.c b/net/sched/sch_generic.c
index ab497ef..720829e 100644
--- a/net/sched/sch_generic.c
+++ b/net/sched/sch_generic.c
@@ -1071,7 +1071,8 @@ static bool some_qdisc_is_busy(struct net_device *dev)
q = dev_queue->qdisc_sleeping;
if (q->flags & TCQ_F_NOLOCK) {
- val = test_bit(__QDISC_STATE_SCHED, &q->state);
+ val = (qdisc_is_running(q) ||
+ test_bit(__QDISC_STATE_SCHED, &q->state));
} else {
root_lock = qdisc_lock(q);
spin_lock_bh(root_lock);
Thanks,
John
^ permalink raw reply related
* Re: correctness of BPF stack size checking logic for multi-function programs?
From: Alexei Starovoitov @ 2017-12-22 3:37 UTC (permalink / raw)
To: Jann Horn
Cc: Alexei Starovoitov, Daniel Borkmann, kernel list,
Network Development
In-Reply-To: <CAG48ez2-PqmcE7zp9W8PvmGJTWzfqg_HzGRQvNOCmcwfUcWn2g@mail.gmail.com>
On Fri, Dec 22, 2017 at 02:14:45AM +0100, Jann Horn wrote:
> Hi!
>
> I saw the recently-added support for multiple functions in a single
> program in BPF. I've stumbled over something that looks like it might
> be a bug; I haven't verified it yet, but I thought I should give you a
> heads-up before this lands in a release in case I'm right. If I'm
> wrong, it might be worth adding a comment to stacksafe() that explains
> why.
>
> stacksafe() has the following code:
>
> /* if explored stack has more populated slots than current stack
> * such stacks are not equivalent
> */
> if (old->allocated_stack > cur->allocated_stack)
> return false;
>
> Note that if the old state had a smaller stack than the new state,
> that is permitted because it is guaranteed that none of the extra
> space in the new state will be used.
>
> However, as far as I can tell, this can be used to smuggle a call
> chain with a total stack size bigger than the permitted maximum
> through the verifier, with code roughly as follows:
>
> void b(void) {
> <allocate 300 bytes stack>
> }
> void main(void) {
> if (<condition>) {
> <allocate 300 bytes stack>
> }
> b();
> }
>
> AFAICS, if the verifier first verifies the branch of main() where
> <condition> is false, it will go down into b, seeing a total stack
> size of around 300 bytes. Afterwards, it will verify the branch of
> main() where <condition> is true, but the states will converge after
> the branch, preventing the verifier from going down into b() again and
> discovering through update_stack_depth() that actually, the total
> stack size is around 600 bytes. From a coarse look, it seems like this
> might be usable to overflow the kernel stack, which would be
> exploitable on systems without vmapped stack?
I'm lost at part 'going down into b() again'..
b() is not going to be processed first.
The verifier always starts from main() and until we add bpf libraries
and dynamic linking the main() has to be placed first in the insn sequence,
otherwise b() (like in above) will be processed by check_cfg() first
and main() declared as dead code and whole thing rejected.
So only valid sequence is:
void main(void) {
if (<condition>) {
<allocate 300 bytes stack>
}
b();
}
void b(void) {
<allocate 300 bytes stack>
}
if the code is structured like:
void main(void) {
if (<condition>) goto alloc;
b:
b();
return;
alloc:
<allocate 300 bytes stack>
goto b;
}
void b(void) {
<allocate 300 bytes stack>
}
then in the fall-through branch the b() will be first
walked with empty caller's stack and the verifier will see 300
alloc inside 'b' and declare it as ok,
then it will reach 'exit' and go back to walk 'alloc:' branch
and will walk into b() again and now it will see 300 + 300,
so I don't think there is a bug here,
but I will rewrite a test case for it unless you beat me to it :)
Please suggest the wording for the comment and where to add it.
I think we're long overdue for the verifier doc update.
The comment at the top of verifier.c is stale.
^ permalink raw reply
* [PATCH V5 net-next 14/17] net: hns3: add Asym Pause support to phy default features
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
From: Fuyun Liang <liangfuyun1@huawei.com>
commit c4fb2cdf575d ("net: hns3: fix a bug for phy supported feature
initialization") adds default supported features for phy, but our hardware
also supports Asym Pause. This patch adds Asym Pause support to phy
default features to prevent Asym Pause can not be advertised when the phy
negotiates flow control.
Fixes: c4fb2cdf575d ("net: hns3: fix a bug for phy supported feature initialization")
Signed-off-by: Fuyun Liang <liangfuyun1@huawei.com>
Signed-off-by: Peng Li <lipeng321@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c | 1 +
1 file changed, 1 insertion(+)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c
index 3745153..c1dea3a 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c
@@ -17,6 +17,7 @@
#define HCLGE_PHY_SUPPORTED_FEATURES (SUPPORTED_Autoneg | \
SUPPORTED_TP | \
SUPPORTED_Pause | \
+ SUPPORTED_Asym_Pause | \
PHY_10BT_FEATURES | \
PHY_100BT_FEATURES | \
PHY_1000BT_FEATURES)
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 12/17] net: hns3: add support for set_pauseparam
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
This patch adds set_pauseparam support for ethtool cmd.
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Fuyun Liang <liangfuyun1@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c | 13 ++++
.../ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 83 ++++++++++++++++++++++
.../net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.c | 2 +-
.../net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.h | 1 +
4 files changed, 98 insertions(+), 1 deletion(-)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
index 2fd2656..b829ec7 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
@@ -559,6 +559,18 @@ static void hns3_get_pauseparam(struct net_device *netdev,
¶m->rx_pause, ¶m->tx_pause);
}
+static int hns3_set_pauseparam(struct net_device *netdev,
+ struct ethtool_pauseparam *param)
+{
+ struct hnae3_handle *h = hns3_get_handle(netdev);
+
+ if (h->ae_algo->ops->set_pauseparam)
+ return h->ae_algo->ops->set_pauseparam(h, param->autoneg,
+ param->rx_pause,
+ param->tx_pause);
+ return -EOPNOTSUPP;
+}
+
static int hns3_get_link_ksettings(struct net_device *netdev,
struct ethtool_link_ksettings *cmd)
{
@@ -880,6 +892,7 @@ void hns3_get_channels(struct net_device *netdev,
.get_ringparam = hns3_get_ringparam,
.set_ringparam = hns3_set_ringparam,
.get_pauseparam = hns3_get_pauseparam,
+ .set_pauseparam = hns3_set_pauseparam,
.get_strings = hns3_get_strings,
.get_ethtool_stats = hns3_get_stats,
.get_sset_count = hns3_get_sset_count,
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index 14e1054..0f55ee6 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -4660,6 +4660,53 @@ static u32 hclge_get_fw_version(struct hnae3_handle *handle)
return hdev->fw_version;
}
+static void hclge_set_flowctrl_adv(struct hclge_dev *hdev, u32 rx_en, u32 tx_en)
+{
+ struct phy_device *phydev = hdev->hw.mac.phydev;
+
+ if (!phydev)
+ return;
+
+ phydev->advertising &= ~(ADVERTISED_Pause | ADVERTISED_Asym_Pause);
+
+ if (rx_en)
+ phydev->advertising |= ADVERTISED_Pause | ADVERTISED_Asym_Pause;
+
+ if (tx_en)
+ phydev->advertising ^= ADVERTISED_Asym_Pause;
+}
+
+static int hclge_cfg_pauseparam(struct hclge_dev *hdev, u32 rx_en, u32 tx_en)
+{
+ enum hclge_fc_mode fc_mode;
+ int ret;
+
+ if (rx_en && tx_en)
+ fc_mode = HCLGE_FC_FULL;
+ else if (rx_en && !tx_en)
+ fc_mode = HCLGE_FC_RX_PAUSE;
+ else if (!rx_en && tx_en)
+ fc_mode = HCLGE_FC_TX_PAUSE;
+ else
+ fc_mode = HCLGE_FC_NONE;
+
+ if (hdev->tm_info.fc_mode == HCLGE_FC_PFC) {
+ hdev->fc_mode_last_time = fc_mode;
+ return 0;
+ }
+
+ ret = hclge_mac_pause_en_cfg(hdev, tx_en, rx_en);
+ if (ret) {
+ dev_err(&hdev->pdev->dev, "configure pauseparam error, ret = %d.\n",
+ ret);
+ return ret;
+ }
+
+ hdev->tm_info.fc_mode = fc_mode;
+
+ return 0;
+}
+
static void hclge_get_pauseparam(struct hnae3_handle *handle, u32 *auto_neg,
u32 *rx_en, u32 *tx_en)
{
@@ -4689,6 +4736,41 @@ static void hclge_get_pauseparam(struct hnae3_handle *handle, u32 *auto_neg,
}
}
+static int hclge_set_pauseparam(struct hnae3_handle *handle, u32 auto_neg,
+ u32 rx_en, u32 tx_en)
+{
+ struct hclge_vport *vport = hclge_get_vport(handle);
+ struct hclge_dev *hdev = vport->back;
+ struct phy_device *phydev = hdev->hw.mac.phydev;
+ u32 fc_autoneg;
+
+ /* Only support flow control negotiation for netdev with
+ * phy attached for now.
+ */
+ if (!phydev)
+ return -EOPNOTSUPP;
+
+ fc_autoneg = hclge_get_autoneg(handle);
+ if (auto_neg != fc_autoneg) {
+ dev_info(&hdev->pdev->dev,
+ "To change autoneg please use: ethtool -s <dev> autoneg <on|off>\n");
+ return -EOPNOTSUPP;
+ }
+
+ if (hdev->tm_info.fc_mode == HCLGE_FC_PFC) {
+ dev_info(&hdev->pdev->dev,
+ "Priority flow control enabled. Cannot set link flow control.\n");
+ return -EOPNOTSUPP;
+ }
+
+ hclge_set_flowctrl_adv(hdev, rx_en, tx_en);
+
+ if (!fc_autoneg)
+ return hclge_cfg_pauseparam(hdev, rx_en, tx_en);
+
+ return phy_start_aneg(phydev);
+}
+
static void hclge_get_ksettings_an_result(struct hnae3_handle *handle,
u8 *auto_neg, u32 *speed, u8 *duplex)
{
@@ -5344,6 +5426,7 @@ static int hclge_set_channels(struct hnae3_handle *handle, u32 new_tqps_num)
.set_autoneg = hclge_set_autoneg,
.get_autoneg = hclge_get_autoneg,
.get_pauseparam = hclge_get_pauseparam,
+ .set_pauseparam = hclge_set_pauseparam,
.set_mtu = hclge_set_mtu,
.reset_queue = hclge_reset_tqp,
.get_stats = hclge_get_stats,
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.c
index 7bfa2e5..7cfe1eb 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.c
@@ -112,7 +112,7 @@ static int hclge_shaper_para_calc(u32 ir, u8 shaper_level,
return 0;
}
-static int hclge_mac_pause_en_cfg(struct hclge_dev *hdev, bool tx, bool rx)
+int hclge_mac_pause_en_cfg(struct hclge_dev *hdev, bool tx, bool rx)
{
struct hclge_desc desc;
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.h b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.h
index bf59961..16f4139 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.h
@@ -118,4 +118,5 @@ struct hclge_port_shapping_cmd {
int hclge_tm_dwrr_cfg(struct hclge_dev *hdev);
int hclge_tm_map_cfg(struct hclge_dev *hdev);
int hclge_tm_init_hw(struct hclge_dev *hdev);
+int hclge_mac_pause_en_cfg(struct hclge_dev *hdev, bool tx, bool rx);
#endif
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 03/17] net: hns3: change the returned tqp number by ethtool -x
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
This patch modifies the return data of get_rxnfc, it will return
the current handle's rss_size but not the total tqp number.
because the tc_size has been change to the log2 of roundup
power of two of rss_size.
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Mingguang Qu <qumingguang@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
index 1b2d79b..2fd2656 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
@@ -730,7 +730,7 @@ static int hns3_get_rxnfc(struct net_device *netdev,
switch (cmd->cmd) {
case ETHTOOL_GRXRINGS:
- cmd->data = h->kinfo.num_tc * h->kinfo.rss_size;
+ cmd->data = h->kinfo.rss_size;
break;
case ETHTOOL_GRXFH:
return h->ae_algo->ops->get_rss_tuple(h, cmd);
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 04/17] net: hns3: free the ring_data structrue when change tqps
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
This patch fixes a memory leak problems in change tqps process,
the function hns3_uninit_all_ring and hns3_init_all_ring
may be called many times.
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Mingguang Qu <qumingguang@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hns3_enet.c | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
index 7e92068..1c93038 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
@@ -2800,8 +2800,12 @@ int hns3_uninit_all_ring(struct hns3_nic_priv *priv)
h->ae_algo->ops->reset_queue(h, i);
hns3_fini_ring(priv->ring_data[i].ring);
+ devm_kfree(priv->dev, priv->ring_data[i].ring);
hns3_fini_ring(priv->ring_data[i + h->kinfo.num_tqps].ring);
+ devm_kfree(priv->dev,
+ priv->ring_data[i + h->kinfo.num_tqps].ring);
}
+ devm_kfree(priv->dev, priv->ring_data);
return 0;
}
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 13/17] net: hns3: add support to update flow control settings after autoneg
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
When auto-negotiation is enabled, the MAC flow control settings is
based on the flow control negotiation result. And it should be configured
after a valid link has been established. This patch adds support to update
flow control settings after auto-negotiation has completed.
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Fuyun Liang <liangfuyun1@huawei.com>
---
.../ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 36 ++++++++++++++++++++++
.../ethernet/hisilicon/hns3/hns3pf/hclge_main.h | 1 +
.../ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c | 4 +++
3 files changed, 41 insertions(+)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index 0f55ee6..bb31212 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -4707,6 +4707,42 @@ static int hclge_cfg_pauseparam(struct hclge_dev *hdev, u32 rx_en, u32 tx_en)
return 0;
}
+int hclge_cfg_flowctrl(struct hclge_dev *hdev)
+{
+ struct phy_device *phydev = hdev->hw.mac.phydev;
+ u16 remote_advertising = 0;
+ u16 local_advertising = 0;
+ u32 rx_pause, tx_pause;
+ u8 flowctl;
+
+ if (!phydev->link || !phydev->autoneg)
+ return 0;
+
+ if (phydev->advertising & ADVERTISED_Pause)
+ local_advertising = ADVERTISE_PAUSE_CAP;
+
+ if (phydev->advertising & ADVERTISED_Asym_Pause)
+ local_advertising |= ADVERTISE_PAUSE_ASYM;
+
+ if (phydev->pause)
+ remote_advertising = LPA_PAUSE_CAP;
+
+ if (phydev->asym_pause)
+ remote_advertising |= LPA_PAUSE_ASYM;
+
+ flowctl = mii_resolve_flowctrl_fdx(local_advertising,
+ remote_advertising);
+ tx_pause = flowctl & FLOW_CTRL_TX;
+ rx_pause = flowctl & FLOW_CTRL_RX;
+
+ if (phydev->duplex == HCLGE_MAC_HALF) {
+ tx_pause = 0;
+ rx_pause = 0;
+ }
+
+ return hclge_cfg_pauseparam(hdev, rx_pause, tx_pause);
+}
+
static void hclge_get_pauseparam(struct hnae3_handle *handle, u32 *auto_neg,
u32 *rx_en, u32 *tx_en)
{
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h
index cda520c..28cc063 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h
@@ -602,4 +602,5 @@ int hclge_set_vf_vlan_common(struct hclge_dev *vport, int vfid,
void hclge_mbx_handler(struct hclge_dev *hdev);
void hclge_reset_tqp(struct hnae3_handle *handle, u16 queue_id);
+int hclge_cfg_flowctrl(struct hclge_dev *hdev);
#endif
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c
index 7069e94..3745153 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c
@@ -183,6 +183,10 @@ static void hclge_mac_adjust_link(struct net_device *netdev)
ret = hclge_cfg_mac_speed_dup(hdev, speed, duplex);
if (ret)
netdev_err(netdev, "failed to adjust link.\n");
+
+ ret = hclge_cfg_flowctrl(hdev);
+ if (ret)
+ netdev_err(netdev, "failed to configure flow control.\n");
}
int hclge_mac_start_phy(struct hclge_dev *hdev)
--
1.9.1
^ permalink raw reply related
* Re: [Patch net-next] net_sched: call qdisc_reset() with qdisc lock
From: Jakub Kicinski @ 2017-12-22 4:06 UTC (permalink / raw)
To: John Fastabend; +Cc: Cong Wang, netdev
In-Reply-To: <bbbffbae-2c05-b07c-21f3-0371f02aa7f7@gmail.com>
[-- Attachment #1: Type: text/plain, Size: 18056 bytes --]
On Thu, 21 Dec 2017 19:36:51 -0800, John Fastabend wrote:
> diff --git a/net/sched/sch_generic.c b/net/sched/sch_generic.c
> index ab497ef..720829e 100644
> --- a/net/sched/sch_generic.c
> +++ b/net/sched/sch_generic.c
> @@ -1071,7 +1071,8 @@ static bool some_qdisc_is_busy(struct net_device *dev)
> q = dev_queue->qdisc_sleeping;
>
> if (q->flags & TCQ_F_NOLOCK) {
> - val = test_bit(__QDISC_STATE_SCHED, &q->state);
> + val = (qdisc_is_running(q) ||
> + test_bit(__QDISC_STATE_SCHED, &q->state));
> } else {
> root_lock = qdisc_lock(q);
> spin_lock_bh(root_lock);
Ah, I just found hpinging the machine with the right .config seems
to be a good trigger. Testing... I'm afraid KASAN splat still there.
Attaching my .config FWIW.
[ 67.870458] ==================================================================
[ 67.878616] BUG: KASAN: slab-out-of-bounds in pfifo_fast_dequeue+0x140/0x2d0
[ 67.886566] Read of size 8 at addr ffff88036f34c040 by task swapper/12/0
[ 67.894123]
[ 67.895854] CPU: 12 PID: 0 Comm: swapper/12 Not tainted 4.15.0-rc3-perf-01035-ge394cb5fbb97-dirty #24
[ 67.906232] Hardware name: Dell Inc. PowerEdge R730/072T6D, BIOS 2.3.4 11/08/2016
[ 67.914665] Call Trace:
[ 67.917462] <IRQ>
[ 67.919778] dump_stack+0xa6/0x118
[ 67.923645] ? _atomic_dec_and_lock+0xe8/0xe8
[ 67.928582] ? pfifo_fast_dequeue+0x140/0x2d0
[ 67.933524] print_address_description+0x6a/0x270
[ 67.938839] ? pfifo_fast_dequeue+0x140/0x2d0
[ 67.943775] kasan_report+0x23f/0x350
[ 67.947933] pfifo_fast_dequeue+0x140/0x2d0
[ 67.952676] ? stack_access_ok+0x3d/0xa0
[ 67.957126] __qdisc_run+0x167/0xa20
[ 67.961188] ? __orc_find+0x6b/0xc0
[ 67.965153] ? sch_direct_xmit+0x3d0/0x3d0
[ 67.969820] ? _raw_spin_unlock+0x73/0xc0
[ 67.974388] ? _raw_spin_trylock+0xe0/0xe0
[ 67.979053] ? deref_stack_reg+0x50/0xd0
[ 67.983528] ? tg3_poll_msix+0x64/0x290 [tg3]
[ 67.988529] ? is_module_text_address+0x11/0x30
[ 67.993682] ? kernel_text_address+0x5a/0x100
[ 67.998631] ? pfifo_fast_enqueue+0x154/0x180
[ 68.003591] __dev_queue_xmit+0x5ae/0x1110
[ 68.008268] ? depot_save_stack+0x12d/0x470
[ 68.013023] ? netdev_pick_tx+0x150/0x150
[ 68.017592] ? __kmalloc_node_track_caller+0x16e/0x2a0
[ 68.023424] ? __kmalloc_reserve.isra.7+0x2e/0x80
[ 68.028769] ? __alloc_skb+0xed/0x390
[ 68.032949] ? sock_wmalloc+0xc2/0x110
[ 68.037227] ? __ip_append_data.isra.3+0xee8/0x1090
[ 68.042768] ? ip_append_data.part.4+0x8b/0xd0
[ 68.047821] ? ip_send_unicast_reply+0x564/0x6d0
[ 68.053071] ? tcp_v4_send_reset+0xa7b/0xd20
[ 68.057929] ? tcp_v4_rcv+0xcce/0x1650
[ 68.062207] ? ip_local_deliver_finish+0x13d/0x3f0
[ 68.067649] ? ip_local_deliver+0xe2/0x280
[ 68.072314] ? ip_rcv_finish+0x5f7/0xa10
[ 68.076785] ? ip_rcv+0x49d/0x780
[ 68.080576] ? __netif_receive_skb_core+0xfa9/0x1bd0
[ 68.086213] ? netif_receive_skb_internal+0x93/0x240
[ 68.091849] ? napi_gro_receive+0x1b3/0x1d0
[ 68.096616] ? tg3_poll_work+0x13e3/0x1d80 [tg3]
[ 68.101867] ? tg3_poll_msix+0x64/0x290 [tg3]
[ 68.106825] ? net_rx_action+0x4a8/0xb00
[ 68.111295] ? __do_softirq+0x17f/0x4de
[ 68.115673] ? irq_exit+0xe1/0xf0
[ 68.119463] ? do_IRQ+0x94/0xe0
[ 68.123059] ? common_interrupt+0x8c/0x8c
[ 68.127631] ? cpuidle_enter_state+0x12a/0x510
[ 68.132687] ? do_idle+0x1af/0x200
[ 68.136574] ? cpu_startup_entry+0xd2/0xe0
[ 68.141240] ? start_secondary+0x271/0x2b0
[ 68.145906] ? secondary_startup_64+0xa5/0xb0
[ 68.150862] ? common_interrupt+0x8c/0x8c
[ 68.155430] ? cpuidle_enter_state+0x12a/0x510
[ 68.160508] ? do_idle+0x1af/0x200
[ 68.164396] ? cpu_startup_entry+0xd2/0xe0
[ 68.169061] ? start_secondary+0x271/0x2b0
[ 68.173726] ? secondary_startup_64+0xa5/0xb0
[ 68.178683] ? ___slab_alloc+0x45d/0x600
[ 68.183155] ? inet_lookup_ifaddr_rcu+0x126/0x170
[ 68.188534] ? memcg_kmem_put_cache+0x63/0x120
[ 68.193587] ? memcg_kmem_get_cache+0x4e0/0x4e0
[ 68.198739] ? __rcu_read_unlock+0x6e/0x120
[ 68.203502] ? memcg_kmem_put_cache+0x63/0x120
[ 68.208571] ? memcg_kmem_get_cache+0x4e0/0x4e0
[ 68.213723] ? __kmalloc_node_track_caller+0x1fe/0x2a0
[ 68.219546] ? __alloc_skb+0xed/0x390
[ 68.223726] ? __kmalloc_reserve.isra.7+0x43/0x80
[ 68.229071] ? memset+0x1f/0x40
[ 68.232667] ? __alloc_skb+0x27e/0x390
[ 68.236944] ? __kmalloc_reserve.isra.7+0x80/0x80
[ 68.242289] ? ktime_get+0x10d/0x1a0
[ 68.246370] ? __rcu_read_unlock+0x6e/0x120
[ 68.251134] ? ip_finish_output2+0x68d/0x7c0
[ 68.255994] ip_finish_output2+0x68d/0x7c0
[ 68.260661] ? ip_send_check+0x60/0x60
[ 68.264937] ? skb_set_owner_w+0x9c/0x120
[ 68.269504] ? sock_wmalloc+0xd5/0x110
[ 68.273782] ? sk_alloc+0x6b0/0x6b0
[ 68.277768] ? ipv4_mtu+0x163/0x200
[ 68.281754] ? ipv4_negative_advice+0x60/0x60
[ 68.286710] ? ip_reply_glue_bits+0x2c/0x50
[ 68.291474] ? __ip_append_data.isra.3+0xdb1/0x1090
[ 68.297014] ? ip_idents_reserve+0x11d/0x1a0
[ 68.301872] ? ipv4_sysctl_rtcache_flush+0x40/0x40
[ 68.307315] ? ip_setup_cork+0x230/0x230
[ 68.311786] ? ip_finish_output+0x39a/0x4c0
[ 68.316582] ip_finish_output+0x39a/0x4c0
[ 68.321150] ? ip_fragment.constprop.5+0xf0/0xf0
[ 68.326398] ? ipv4_mtu+0x163/0x200
[ 68.330384] ? __ip_select_ident+0xf8/0x180
[ 68.335147] ? find_exception+0x270/0x270
[ 68.339716] ? ipv4_mtu+0x163/0x200
[ 68.343699] ? ip_send_check+0x20/0x60
[ 68.347978] ip_output+0x106/0x280
[ 68.351865] ? ip_mc_output+0x750/0x750
[ 68.356258] ? ip_append_page+0x6d0/0x6d0
[ 68.360825] ? ip_append_data.part.4+0x8b/0xd0
[ 68.365879] ip_send_skb+0x29/0x70
[ 68.369766] ? ip_push_pending_frames+0x2e/0x50
[ 68.374918] ip_send_unicast_reply+0x64e/0x6d0
[ 68.379973] ? ip_make_skb+0x1d0/0x1d0
[ 68.384257] ? ip_local_deliver+0xe2/0x280
[ 68.388920] ? ip_rcv+0x49d/0x780
[ 68.392711] ? __netif_receive_skb_core+0xfa9/0x1bd0
[ 68.398348] ? napi_gro_receive+0x1b3/0x1d0
[ 68.403113] ? tg3_poll_work+0x13e3/0x1d80 [tg3]
[ 68.408358] ? tg3_poll_msix+0x64/0x290 [tg3]
[ 68.413316] ? net_rx_action+0x4a8/0xb00
[ 68.417788] ? __do_softirq+0x17f/0x4de
[ 68.422163] ? cpuidle_enter_state+0x12a/0x510
[ 68.427218] ? do_idle+0x1af/0x200
[ 68.431104] ? cpu_startup_entry+0xd2/0xe0
[ 68.435769] ? start_secondary+0x271/0x2b0
[ 68.440453] ? map_id_range_down+0x186/0x1b0
[ 68.445311] ? __put_user_ns+0x30/0x30
[ 68.449589] ? trace_event_raw_event_rcu_torture_read+0x190/0x190
[ 68.456529] tcp_v4_send_reset+0xa7b/0xd20
[ 68.461196] ? tcp_v4_reqsk_send_ack+0x1a0/0x1a0
[ 68.466444] ? __inet_lookup_listener+0x1e5/0x520
[ 68.471790] ? sock_edemux+0x20/0x20
[ 68.475873] ? reweight_entity+0x630/0x630
[ 68.480569] ? rb_insert_color_cached+0x6f3/0x7a0
[ 68.485914] ? rb_insert_color+0x770/0x770
[ 68.490581] ? tcp_v4_rcv+0xcce/0x1650
[ 68.494858] tcp_v4_rcv+0xcce/0x1650
[ 68.498941] ? tcp_v4_early_demux+0x350/0x350
[ 68.503900] ? raw_rcv+0x1b0/0x1b0
[ 68.507787] ? reweight_entity+0x393/0x630
[ 68.512482] ? update_curr+0xa9/0x3c0
[ 68.516662] ? rb_insert_color+0x770/0x770
[ 68.521328] ? __inet_lookup_established+0x12e/0x3d0
[ 68.526966] ? __udp4_lib_rcv+0x1150/0x1150
[ 68.531719] ? load_too_imbalanced+0xd0/0xd0
[ 68.536581] ip_local_deliver_finish+0x13d/0x3f0
[ 68.541921] ? inet_del_offload+0x40/0x40
[ 68.546489] ? update_curr+0xa9/0x3c0
[ 68.550667] ? __rcu_read_unlock+0x6e/0x120
[ 68.555431] ? trace_event_raw_event_rcu_torture_read+0x190/0x190
[ 68.562332] ip_local_deliver+0xe2/0x280
[ 68.566804] ? ip_call_ra_chain+0x2e0/0x2e0
[ 68.571567] ? ip_route_input_noref+0x95/0xd0
[ 68.576563] ? ip_route_input_rcu+0x1570/0x1570
[ 68.581716] ip_rcv_finish+0x5f7/0xa10
[ 68.585983] ? put_prev_task_fair+0x50/0x50
[ 68.590747] ? ip_local_deliver_finish+0x3f0/0x3f0
[ 68.596204] ? account_entity_enqueue+0x1d2/0x240
[ 68.601551] ? load_too_imbalanced+0xd0/0xd0
[ 68.606409] ? __update_load_avg_cfs_rq.isra.5+0x2b6/0x2c0
[ 68.612628] ? __enqueue_entity+0x93/0xc0
[ 68.617196] ? tcp_v4_send_synack+0x1a0/0x1a0
[ 68.622153] ? enqueue_entity+0xc16/0x1450
[ 68.626817] ? rb_insert_color_cached+0x6f3/0x7a0
[ 68.632180] ? rb_insert_color+0x770/0x770
[ 68.636847] ? __dev_queue_xmit+0x61d/0x1110
[ 68.641706] ? put_prev_task_fair+0x50/0x50
[ 68.646468] ip_rcv+0x49d/0x780
[ 68.650066] ? ip_local_deliver+0x280/0x280
[ 68.654830] ? idle_cpu+0x100/0x100
[ 68.658818] ? __alloc_pages_nodemask+0x316/0x1d30
[ 68.664277] ? enqueue_task_fair+0x2d9/0x10d0
[ 68.669235] ? smp_thermal_interrupt+0x230/0x230
[ 68.674484] ? update_cfs_group+0x232/0x290
[ 68.679246] ? rb_insert_color+0x770/0x770
[ 68.683910] ? reweight_entity+0x630/0x630
[ 68.688583] ? ip_local_deliver+0x280/0x280
[ 68.693346] __netif_receive_skb_core+0xfa9/0x1bd0
[ 68.698791] ? flush_backlog+0x250/0x250
[ 68.703262] ? 0xffffffffa0000000
[ 68.707052] ? update_curr+0xa9/0x3c0
[ 68.711230] ? stack_access_ok+0x3d/0xa0
[ 68.715702] ? __module_address+0x232/0x330
[ 68.720498] ? modules_open+0x60/0x60
[ 68.724678] ? __accumulate_pelt_segments+0x47/0xd0
[ 68.730217] ? __module_address+0x232/0x330
[ 68.734980] ? stack_access_ok+0x3d/0xa0
[ 68.739450] ? deref_stack_reg+0x98/0xd0
[ 68.743922] ? __read_once_size_nocheck.constprop.3+0x10/0x10
[ 68.750435] ? get_stack_info+0x37/0x150
[ 68.754906] ? __orc_find+0x6b/0xc0
[ 68.758891] ? secondary_startup_64+0xa4/0xb0
[ 68.763848] ? unwind_next_frame+0xcd/0xbf0
[ 68.768610] ? cpuidle_enter_state+0x12a/0x510
[ 68.773667] ? tg3_poll_msix+0x64/0x290 [tg3]
[ 68.778623] ? deref_stack_reg+0xd0/0xd0
[ 68.783093] ? __build_skb+0x85/0x210
[ 68.787276] ? tg3_poll_msix+0x64/0x290 [tg3]
[ 68.792242] ? is_module_text_address+0x11/0x30
[ 68.797393] ? kernel_text_address+0x5a/0x100
[ 68.802350] ? _mix_pool_bytes+0x1fc/0x260
[ 68.807019] ? tg3_poll_msix+0x64/0x290 [tg3]
[ 68.811975] ? __build_skb+0x85/0x210
[ 68.816155] ? __save_stack_trace+0x73/0xd0
[ 68.831167] ? depot_save_stack+0x12d/0x470
[ 68.835929] ? __build_skb+0x85/0x210
[ 68.840108] ? kasan_kmalloc+0x142/0x170
[ 68.844591] ? kmem_cache_alloc+0xb3/0x1c0
[ 68.849247] ? __build_skb+0x85/0x210
[ 68.853425] ? __netdev_alloc_skb+0xeb/0x150
[ 68.858287] ? tg3_poll_work+0x1113/0x1d80 [tg3]
[ 68.863535] ? __rcu_read_unlock+0x6e/0x120
[ 68.868299] ? trace_event_raw_event_rcu_torture_read+0x190/0x190
[ 68.875199] ? tcp_gro_receive+0x3cd/0x550
[ 68.879865] ? tcp4_gro_receive+0x25/0x350
[ 68.884566] ? start_secondary+0x271/0x2b0
[ 68.889230] ? secondary_startup_64+0xa5/0xb0
[ 68.894187] ? inet_gro_receive+0x19a/0x5e0
[ 68.898950] ? ktime_get_with_offset+0x144/0x1e0
[ 68.904217] ? ktime_get_resolution_ns+0xf0/0xf0
[ 68.909457] ? trace_event_raw_event_rcu_torture_read+0x190/0x190
[ 68.916360] ? trace_event_raw_event_rcu_torture_read+0x190/0x190
[ 68.923261] ? netif_receive_skb_internal+0x93/0x240
[ 68.928897] netif_receive_skb_internal+0x93/0x240
[ 68.934340] ? dev_cpu_dead+0x470/0x470
[ 68.938715] ? __build_skb+0x85/0x210
[ 68.942895] ? net_rx_action+0xb00/0xb00
[ 68.947366] ? memset+0x1f/0x40
[ 68.950962] ? __build_skb+0x1b7/0x210
[ 68.955238] ? skb_push+0x80/0x80
[ 68.959029] napi_gro_receive+0x1b3/0x1d0
[ 68.963597] ? dev_gro_receive+0xc50/0xc50
[ 68.968284] tg3_poll_work+0x13e3/0x1d80 [tg3]
[ 68.973346] ? tg3_poll_controller+0x90/0x90 [tg3]
[ 68.978787] ? enqueue_entity+0x1450/0x1450
[ 68.983551] ? napi_complete_done+0x159/0x2e0
[ 68.988547] ? napi_gro_flush+0xd0/0xd0
[ 68.992922] ? rb_insert_color+0x12e/0x770
[ 68.997588] ? rb_first_postorder+0x50/0x50
[ 69.002353] ? rcu_segcblist_extract_pend_cbs+0xa0/0xa0
[ 69.008282] ? dequeue_rt_stack+0x103/0x5a0
[ 69.013050] tg3_poll_msix+0x64/0x290 [tg3]
[ 69.017814] net_rx_action+0x4a8/0xb00
[ 69.022093] ? napi_complete_done+0x2e0/0x2e0
[ 69.027108] ? read_exit_mmio+0x140/0x140 [kvm]
[ 69.032277] ? update_max_interval+0x40/0x40
[ 69.037136] ? wait_rcu_exp_gp+0x60/0x60
[ 69.041607] ? _raw_spin_unlock+0xc0/0xc0
[ 69.046175] ? rcu_segcblist_future_gp_needed+0x48/0x80
[ 69.052105] ? cpu_needs_another_gp+0x29e/0x2b0
[ 69.057255] ? print_other_cpu_stall+0x870/0x870
[ 69.062503] ? __wake_up_common+0xa9/0x2d0
[ 69.067169] ? __note_gp_changes+0x670/0x670
[ 69.072028] ? remove_wait_queue+0x160/0x160
[ 69.076889] ? _raw_spin_unlock+0xc0/0xc0
[ 69.081457] ? resched_curr+0x84/0x1b0
[ 69.085732] ? wake_q_add+0x50/0x50
[ 69.089720] ? cyc2ns_read_end+0x20/0x20
[ 69.094192] ? _raw_spin_unlock+0xc0/0xc0
[ 69.098759] ? _raw_spin_trylock+0xe0/0xe0
[ 69.103425] ? native_sched_clock_from_tsc+0x130/0x160
[ 69.109258] ? sched_clock_cpu+0x14/0xf0
[ 69.113730] ? try_to_wake_up+0x4a9/0x7f0
[ 69.118300] ? raise_softirq_irqoff+0x40/0x40
[ 69.123257] ? migrate_swap_stop+0x3b0/0x3b0
[ 69.128117] ? crng_reseed+0x3d0/0x3d0
[ 69.132398] ? _raw_spin_unlock+0xc0/0xc0
[ 69.136966] ? cyc2ns_read_begin+0x20/0x90
[ 69.141633] ? add_interrupt_randomness+0x1cd/0x3d0
[ 69.147177] ? tg3_interrupt_tagged+0x1b0/0x1b0 [tg3]
[ 69.152911] ? xfer_secondary_pool+0x70/0x70
[ 69.157771] ? irq_wait_for_poll+0xf0/0xf0
[ 69.162437] __do_softirq+0x17f/0x4de
[ 69.166618] ? __softirqentry_text_start+0x8/0x8
[ 69.171866] ? handle_irq_event_percpu+0xb9/0xf0
[ 69.177116] ? __handle_irq_event_percpu+0x390/0x390
[ 69.182745] ? nr_iowait+0x110/0x110
[ 69.186828] ? _raw_spin_unlock+0x73/0xc0
[ 69.191397] ? _raw_spin_trylock+0xe0/0xe0
[ 69.196062] ? handle_irq_event+0x79/0x90
[ 69.200629] ? handle_edge_irq+0x166/0x2f0
[ 69.205295] irq_exit+0xe1/0xf0
[ 69.208892] do_IRQ+0x94/0xe0
[ 69.212295] common_interrupt+0x8c/0x8c
[ 69.216669] </IRQ>
[ 69.219100] RIP: 0010:cpuidle_enter_state+0x12a/0x510
[ 69.224835] RSP: 0018:ffff88036c7cfd08 EFLAGS: 00000246 ORIG_RAX: ffffffffffffffdd
[ 69.233409] RAX: 0000000000000000 RBX: ffffe8fb00b060e0 RCX: ffffffffa01329f5
[ 69.241476] RDX: dffffc0000000000 RSI: dffffc0000000000 RDI: ffff8803703246e8
[ 69.249542] RBP: 1ffff1006d8f9fa6 R08: fffffbfff43429f8 R09: fffffbfff43429f8
[ 69.257608] R10: ffff88036c7cfcc8 R11: fffffbfff43429f7 R12: 0000000fcd62a077
[ 69.265673] R13: 0000000000000002 R14: 0000000000000002 R15: ffffffffa183eac0
[ 69.273741] ? sched_idle_set_state+0x25/0x30
[ 69.278699] ? cpuidle_enter_state+0x106/0x510
[ 69.283754] ? cpuidle_enter_s2idle+0x130/0x130
[ 69.288906] ? rcu_eqs_enter_common.constprop.62+0xd1/0x1e0
[ 69.295223] ? rcu_gp_init+0xf70/0xf70
[ 69.299499] ? sched_set_stop_task+0x160/0x160
[ 69.304586] do_idle+0x1af/0x200
[ 69.308287] cpu_startup_entry+0xd2/0xe0
[ 69.312759] ? cpu_in_idle+0x20/0x20
[ 69.316842] ? _raw_spin_trylock+0xe0/0xe0
[ 69.321508] ? memcpy+0x34/0x50
[ 69.325107] start_secondary+0x271/0x2b0
[ 69.329577] ? set_cpu_sibling_map+0x840/0x840
[ 69.334633] secondary_startup_64+0xa5/0xb0
[ 69.339387]
[ 69.341136] Allocated by task 844:
[ 69.345024] __kmalloc+0xfa/0x230
[ 69.348815] pfifo_fast_init+0x69/0x160
[ 69.353190] qdisc_create_dflt+0x97/0xc0
[ 69.357661] mq_init+0x19f/0x1f0
[ 69.361356] qdisc_create_dflt+0x97/0xc0
[ 69.365825] dev_activate+0x48e/0x4e0
[ 69.370005] __dev_open+0x19e/0x210
[ 69.373989] __dev_change_flags+0x3b5/0x3f0
[ 69.378751] dev_change_flags+0x50/0xa0
[ 69.383126] do_setlink+0x5eb/0x1cf0
[ 69.387209] rtnl_newlink+0x9d5/0xe40
[ 69.391390] rtnetlink_rcv_msg+0x37c/0x7e0
[ 69.396122] netlink_rcv_skb+0x122/0x230
[ 69.400594] netlink_unicast+0x2ae/0x360
[ 69.405066] netlink_sendmsg+0x5d5/0x620
[ 69.409536] sock_sendmsg+0x64/0x80
[ 69.413520] ___sys_sendmsg+0x4a8/0x500
[ 69.417894] __sys_sendmsg+0xa9/0x140
[ 69.422073] entry_SYSCALL_64_fastpath+0x1e/0x81
[ 69.427319]
[ 69.429067] Freed by task 1:
[ 69.432371] kfree+0x8d/0x1c0
[ 69.435775] erst_reader+0x7ef/0x980
[ 69.439857] pstore_get_backend_records+0xdf/0x370
[ 69.445303] pstore_get_records+0x69/0x90
[ 69.449872] pstore_fill_super+0xfe/0x110
[ 69.454441] mount_single+0x60/0xe0
[ 69.458426] mount_fs+0x48/0x190
[ 69.462122] vfs_kern_mount.part.7+0x9f/0x210
[ 69.467079] do_mount+0x945/0x1690
[ 69.470965] SyS_mount+0x55/0xd0
[ 69.474658] entry_SYSCALL_64_fastpath+0x1e/0x81
[ 69.479904]
[ 69.481652] The buggy address belongs to the object at ffff88036f34a100
[ 69.481652] which belongs to the cache kmalloc-8192 of size 8192
[ 69.495958] The buggy address is located 8000 bytes inside of
[ 69.495958] 8192-byte region [ffff88036f34a100, ffff88036f34c100)
[ 69.509388] The buggy address belongs to the page:
[ 69.514832] page:0000000086a349ff count:1 mapcount:0 mapping: (null) index:0x0 compound_mapcount: 0
[ 69.525933] flags: 0x2ffff0000008100(slab|head)
[ 69.531084] raw: 02ffff0000008100 0000000000000000 0000000000000000 0000000100030003
[ 69.539852] raw: dead000000000100 dead000000000200 ffff88036fc0e680 0000000000000000
[ 69.548640] page dumped because: kasan: bad access detected
[ 69.554955]
[ 69.556704] Memory state around the buggy address:
[ 69.562147] ffff88036f34bf00: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
[ 69.570331] ffff88036f34bf80: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
[ 69.578515] >ffff88036f34c000: 00 00 00 00 00 00 00 00 fc fc fc fc fc fc fc fc
[ 69.586699] ^
[ 69.592725] ffff88036f34c080: fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc
[ 69.600901] ffff88036f34c100: fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc
[ 69.609084] ==================================================================
[-- Attachment #2: .config.gz --]
[-- Type: application/gzip, Size: 27625 bytes --]
^ permalink raw reply
* [PATCH net] RDS: Check cmsg_len before dereferencing CMSG_DATA
From: Avinash Repaka @ 2017-12-22 4:17 UTC (permalink / raw)
To: Santosh Shilimkar, David S. Miller, netdev-u79uwXL29TY76Z2rM5mHXA,
linux-rdma-u79uwXL29TY76Z2rM5mHXA,
rds-devel-N0ozoZBvEnrZJqsBc5GL+g,
linux-kernel-u79uwXL29TY76Z2rM5mHXA
Cc: avinash.repaka-QHcLZuEGTsvQT0dZR+AlfA
RDS currently doesn't check if the length of the control message is
large enough to hold the required data, before dereferencing the control
message data. This results in following crash:
BUG: KASAN: stack-out-of-bounds in rds_rdma_bytes net/rds/send.c:1013
[inline]
BUG: KASAN: stack-out-of-bounds in rds_sendmsg+0x1f02/0x1f90
net/rds/send.c:1066
Read of size 8 at addr ffff8801c928fb70 by task syzkaller455006/3157
CPU: 0 PID: 3157 Comm: syzkaller455006 Not tainted 4.15.0-rc3+ #161
Hardware name: Google Google Compute Engine/Google Compute Engine, BIOS
Google 01/01/2011
Call Trace:
__dump_stack lib/dump_stack.c:17 [inline]
dump_stack+0x194/0x257 lib/dump_stack.c:53
print_address_description+0x73/0x250 mm/kasan/report.c:252
kasan_report_error mm/kasan/report.c:351 [inline]
kasan_report+0x25b/0x340 mm/kasan/report.c:409
__asan_report_load8_noabort+0x14/0x20 mm/kasan/report.c:430
rds_rdma_bytes net/rds/send.c:1013 [inline]
rds_sendmsg+0x1f02/0x1f90 net/rds/send.c:1066
sock_sendmsg_nosec net/socket.c:628 [inline]
sock_sendmsg+0xca/0x110 net/socket.c:638
___sys_sendmsg+0x320/0x8b0 net/socket.c:2018
__sys_sendmmsg+0x1ee/0x620 net/socket.c:2108
SYSC_sendmmsg net/socket.c:2139 [inline]
SyS_sendmmsg+0x35/0x60 net/socket.c:2134
entry_SYSCALL_64_fastpath+0x1f/0x96
RIP: 0033:0x43fe49
RSP: 002b:00007fffbe244ad8 EFLAGS: 00000217 ORIG_RAX: 0000000000000133
RAX: ffffffffffffffda RBX: 00000000004002c8 RCX: 000000000043fe49
RDX: 0000000000000001 RSI: 000000002020c000 RDI: 0000000000000003
RBP: 00000000006ca018 R08: 0000000000000000 R09: 0000000000000000
R10: 0000000000000000 R11: 0000000000000217 R12: 00000000004017b0
R13: 0000000000401840 R14: 0000000000000000 R15: 0000000000000000
To fix this, we verify that the cmsg_len is large enough to hold the
data to be read, before proceeding further.
Reported-by: syzbot <syzkaller-bugs-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org>
Signed-off-by: Avinash Repaka <avinash.repaka-QHcLZuEGTsvQT0dZR+AlfA@public.gmane.org>
---
net/rds/send.c | 3 +++
1 file changed, 3 insertions(+)
diff --git a/net/rds/send.c b/net/rds/send.c
index b52cdc8..f72466c 100644
--- a/net/rds/send.c
+++ b/net/rds/send.c
@@ -1009,6 +1009,9 @@ static int rds_rdma_bytes(struct msghdr *msg, size_t *rdma_bytes)
continue;
if (cmsg->cmsg_type == RDS_CMSG_RDMA_ARGS) {
+ if (cmsg->cmsg_len <
+ CMSG_LEN(sizeof(struct rds_rdma_args)))
+ return -EINVAL;
args = CMSG_DATA(cmsg);
*rdma_bytes += args->remote_vec.bytes;
}
--
2.4.11
--
To unsubscribe from this list: send the line "unsubscribe linux-rdma" 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 related
* [PATCH V5 net-next 00/17] add some features and fix some bugs for HNS3 driver
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
This patchset adds some new feature support and fixes some bugs:
[Patch 1/17 - 5/17] add the support to modify/query the tqp number
through ethtool -L/l command, and also fix some related bugs for
change tqp number.
[Patch 6/17 - 9-17] add support vlan tag offload on tx&&rx direction
for pf, and fix some related bugs.
[patch 10/17 - 11/17] fix bugs for auto negotiation.
[patch 12/17] adds support for ethtool command set_pauseparam.
[patch 13/17 - 14/17] add support to update flow control settings after
autoneg.
[patch 15/17 - 17/17] fix some other bugs in net-next.
---
Change Log:
V4 -> V5:
1. change the name spelling of Peng Li.
V3 -> V4:
1. change the name spelling of Mingguang Qu and Jian Shen.
V2 -> V3:
1. order local variables requested by David Miller.
2. use "int" for index iteration loops requested by David Miller.
V1 -> V2:
1. fix the comments from Sergei Shtylyov.
---
Fuyun Liang (3):
net: hns3: cleanup mac auto-negotiation state query
net: hns3: fix for getting auto-negotiation state in hclge_get_autoneg
net: hns3: add Asym Pause support to phy default features
Peng Li (14):
net: hns3: add support to query tqps number
net: hns3: add support to modify tqps number
net: hns3: change the returned tqp number by ethtool -x
net: hns3: free the ring_data structrue when change tqps
net: hns3: get rss_size_max from configuration but not hardcode
net: hns3: add a mask initialization for mac_vlan table
net: hns3: add vlan offload config command
net: hns3: add ethtool related offload command
net: hns3: add handling vlan tag offload in bd
net: hns3: add support for set_pauseparam
net: hns3: add support to update flow control settings after autoneg
net: hns3: add support for querying advertised pause frame by ethtool
ethx
net: hns3: Increase the default depth of bucket for TM shaper
net: hns3: change TM sched mode to TC-based mode when SRIOV enabled
drivers/net/ethernet/hisilicon/hns3/hnae3.h | 10 +
drivers/net/ethernet/hisilicon/hns3/hns3_enet.c | 225 ++++++++-
drivers/net/ethernet/hisilicon/hns3/hns3_enet.h | 2 +
drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c | 41 +-
.../net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h | 57 +++
.../ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 514 +++++++++++++++++++--
.../ethernet/hisilicon/hns3/hns3pf/hclge_main.h | 38 ++
.../ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c | 5 +
.../net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.c | 6 +-
.../net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.h | 1 +
10 files changed, 855 insertions(+), 44 deletions(-)
--
1.9.1
^ permalink raw reply
* [PATCH V5 net-next 01/17] net: hns3: add support to query tqps number
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
This patch adds the support to query tqps number for PF driver
by using ehtool -l command.
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Mingguang Qu <qumingguang@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hnae3.h | 2 ++
drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c | 10 ++++++++++
.../net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 21 +++++++++++++++++++++
3 files changed, 33 insertions(+)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hnae3.h b/drivers/net/ethernet/hisilicon/hns3/hnae3.h
index a9e2b32..d887721 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hnae3.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hnae3.h
@@ -386,6 +386,8 @@ struct hnae3_ae_ops {
u16 vlan, u8 qos, __be16 proto);
void (*reset_event)(struct hnae3_handle *handle,
enum hnae3_reset_type reset);
+ void (*get_channels)(struct hnae3_handle *handle,
+ struct ethtool_channels *ch);
};
struct hnae3_dcb_ops {
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
index 65a69b4..23af36c 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
@@ -849,6 +849,15 @@ static int hns3_nway_reset(struct net_device *netdev)
return genphy_restart_aneg(phy);
}
+void hns3_get_channels(struct net_device *netdev,
+ struct ethtool_channels *ch)
+{
+ struct hnae3_handle *h = hns3_get_handle(netdev);
+
+ if (h->ae_algo->ops->get_channels)
+ h->ae_algo->ops->get_channels(h, ch);
+}
+
static const struct ethtool_ops hns3vf_ethtool_ops = {
.get_drvinfo = hns3_get_drvinfo,
.get_ringparam = hns3_get_ringparam,
@@ -883,6 +892,7 @@ static int hns3_nway_reset(struct net_device *netdev)
.get_link_ksettings = hns3_get_link_ksettings,
.set_link_ksettings = hns3_set_link_ksettings,
.nway_reset = hns3_nway_reset,
+ .get_channels = hns3_get_channels,
};
void hns3_ethtool_set_ops(struct net_device *netdev)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index e97fd66..a3101bc 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -5002,6 +5002,26 @@ static void hclge_uninit_ae_dev(struct hnae3_ae_dev *ae_dev)
ae_dev->priv = NULL;
}
+static u32 hclge_get_max_channels(struct hnae3_handle *handle)
+{
+ struct hnae3_knic_private_info *kinfo = &handle->kinfo;
+ struct hclge_vport *vport = hclge_get_vport(handle);
+ struct hclge_dev *hdev = vport->back;
+
+ return min_t(u32, hdev->rss_size_max * kinfo->num_tc, hdev->num_tqps);
+}
+
+static void hclge_get_channels(struct hnae3_handle *handle,
+ struct ethtool_channels *ch)
+{
+ struct hclge_vport *vport = hclge_get_vport(handle);
+
+ ch->max_combined = hclge_get_max_channels(handle);
+ ch->other_count = 1;
+ ch->max_other = 1;
+ ch->combined_count = vport->alloc_tqps;
+}
+
static const struct hnae3_ae_ops hclge_ops = {
.init_ae_dev = hclge_init_ae_dev,
.uninit_ae_dev = hclge_uninit_ae_dev,
@@ -5046,6 +5066,7 @@ static void hclge_uninit_ae_dev(struct hnae3_ae_dev *ae_dev)
.set_vlan_filter = hclge_set_port_vlan_filter,
.set_vf_vlan_filter = hclge_set_vf_vlan_filter,
.reset_event = hclge_reset_event,
+ .get_channels = hclge_get_channels,
};
static struct hnae3_ae_algo ae_algo = {
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 02/17] net: hns3: add support to modify tqps number
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
This patch adds the support to change tqps number for PF driver
by using ehtool -L command.
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Mingguang Qu <qumingguang@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hnae3.h | 3 +
drivers/net/ethernet/hisilicon/hns3/hns3_enet.c | 122 +++++++++++++++++++++
drivers/net/ethernet/hisilicon/hns3/hns3_enet.h | 2 +
drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c | 1 +
.../ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 112 +++++++++++++++++++
5 files changed, 240 insertions(+)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hnae3.h b/drivers/net/ethernet/hisilicon/hns3/hnae3.h
index d887721..a5d3d22 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hnae3.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hnae3.h
@@ -388,6 +388,9 @@ struct hnae3_ae_ops {
enum hnae3_reset_type reset);
void (*get_channels)(struct hnae3_handle *handle,
struct ethtool_channels *ch);
+ void (*get_tqps_and_rss_info)(struct hnae3_handle *h,
+ u16 *free_tqps, u16 *max_rss_size);
+ int (*set_channels)(struct hnae3_handle *handle, u32 new_tqps_num);
};
struct hnae3_dcb_ops {
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
index c2c1323..7e92068 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
@@ -2651,6 +2651,19 @@ static int hns3_get_ring_config(struct hns3_nic_priv *priv)
return ret;
}
+static void hns3_put_ring_config(struct hns3_nic_priv *priv)
+{
+ struct hnae3_handle *h = priv->ae_handle;
+ int i;
+
+ for (i = 0; i < h->kinfo.num_tqps; i++) {
+ devm_kfree(priv->dev, priv->ring_data[i].ring);
+ devm_kfree(priv->dev,
+ priv->ring_data[i + h->kinfo.num_tqps].ring);
+ }
+ devm_kfree(priv->dev, priv->ring_data);
+}
+
static int hns3_alloc_ring_memory(struct hns3_enet_ring *ring)
{
int ret;
@@ -3162,6 +3175,115 @@ static int hns3_reset_notify(struct hnae3_handle *handle,
return ret;
}
+static u16 hns3_get_max_available_channels(struct net_device *netdev)
+{
+ struct hnae3_handle *h = hns3_get_handle(netdev);
+ u16 free_tqps, max_rss_size, max_tqps;
+
+ h->ae_algo->ops->get_tqps_and_rss_info(h, &free_tqps, &max_rss_size);
+ max_tqps = h->kinfo.num_tc * max_rss_size;
+
+ return min_t(u16, max_tqps, (free_tqps + h->kinfo.num_tqps));
+}
+
+static int hns3_modify_tqp_num(struct net_device *netdev, u16 new_tqp_num)
+{
+ struct hns3_nic_priv *priv = netdev_priv(netdev);
+ struct hnae3_handle *h = hns3_get_handle(netdev);
+ int ret;
+
+ ret = h->ae_algo->ops->set_channels(h, new_tqp_num);
+ if (ret)
+ return ret;
+
+ ret = hns3_get_ring_config(priv);
+ if (ret)
+ return ret;
+
+ ret = hns3_nic_init_vector_data(priv);
+ if (ret)
+ goto err_uninit_vector;
+
+ ret = hns3_init_all_ring(priv);
+ if (ret)
+ goto err_put_ring;
+
+ return 0;
+
+err_put_ring:
+ hns3_put_ring_config(priv);
+err_uninit_vector:
+ hns3_nic_uninit_vector_data(priv);
+ return ret;
+}
+
+static int hns3_adjust_tqps_num(u8 num_tc, u32 new_tqp_num)
+{
+ return (new_tqp_num / num_tc) * num_tc;
+}
+
+int hns3_set_channels(struct net_device *netdev,
+ struct ethtool_channels *ch)
+{
+ struct hns3_nic_priv *priv = netdev_priv(netdev);
+ struct hnae3_handle *h = hns3_get_handle(netdev);
+ struct hnae3_knic_private_info *kinfo = &h->kinfo;
+ bool if_running = netif_running(netdev);
+ u32 new_tqp_num = ch->combined_count;
+ u16 org_tqp_num;
+ int ret;
+
+ if (ch->rx_count || ch->tx_count)
+ return -EINVAL;
+
+ if (new_tqp_num > hns3_get_max_available_channels(netdev) ||
+ new_tqp_num < kinfo->num_tc) {
+ dev_err(&netdev->dev,
+ "Change tqps fail, the tqp range is from %d to %d",
+ kinfo->num_tc,
+ hns3_get_max_available_channels(netdev));
+ return -EINVAL;
+ }
+
+ new_tqp_num = hns3_adjust_tqps_num(kinfo->num_tc, new_tqp_num);
+ if (kinfo->num_tqps == new_tqp_num)
+ return 0;
+
+ if (if_running)
+ dev_close(netdev);
+
+ hns3_clear_all_ring(h);
+
+ ret = hns3_nic_uninit_vector_data(priv);
+ if (ret) {
+ dev_err(&netdev->dev,
+ "Unbind vector with tqp fail, nothing is changed");
+ goto open_netdev;
+ }
+
+ hns3_uninit_all_ring(priv);
+
+ org_tqp_num = h->kinfo.num_tqps;
+ ret = hns3_modify_tqp_num(netdev, new_tqp_num);
+ if (ret) {
+ ret = hns3_modify_tqp_num(netdev, org_tqp_num);
+ if (ret) {
+ /* If revert to old tqp failed, fatal error occurred */
+ dev_err(&netdev->dev,
+ "Revert to old tqp num fail, ret=%d", ret);
+ return ret;
+ }
+ dev_info(&netdev->dev,
+ "Change tqp num fail, Revert to old tqp num");
+ }
+
+open_netdev:
+ if (if_running)
+ dev_open(netdev);
+
+ return ret;
+}
+
static const struct hnae3_client_ops client_ops = {
.init_instance = hns3_client_init,
.uninit_instance = hns3_client_uninit,
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.h b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.h
index 8a9de75..a2a7ea3 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.h
@@ -595,6 +595,8 @@ static inline void hns3_write_reg(void __iomem *base, u32 reg, u32 value)
(((struct hns3_nic_priv *)netdev_priv(ndev))->ae_handle)
void hns3_ethtool_set_ops(struct net_device *netdev);
+int hns3_set_channels(struct net_device *netdev,
+ struct ethtool_channels *ch);
bool hns3_clean_tx_ring(struct hns3_enet_ring *ring, int budget);
int hns3_init_all_ring(struct hns3_nic_priv *priv);
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
index 23af36c..1b2d79b 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
@@ -893,6 +893,7 @@ void hns3_get_channels(struct net_device *netdev,
.set_link_ksettings = hns3_set_link_ksettings,
.nway_reset = hns3_nway_reset,
.get_channels = hns3_get_channels,
+ .set_channels = hns3_set_channels,
};
void hns3_ethtool_set_ops(struct net_device *netdev)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index a3101bc..7fab102 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -5022,6 +5022,116 @@ static void hclge_get_channels(struct hnae3_handle *handle,
ch->combined_count = vport->alloc_tqps;
}
+static void hclge_get_tqps_and_rss_info(struct hnae3_handle *handle,
+ u16 *free_tqps, u16 *max_rss_size)
+{
+ struct hclge_vport *vport = hclge_get_vport(handle);
+ struct hclge_dev *hdev = vport->back;
+ u16 temp_tqps = 0;
+ int i;
+
+ for (i = 0; i < hdev->num_tqps; i++) {
+ if (!hdev->htqp[i].alloced)
+ temp_tqps++;
+ }
+ *free_tqps = temp_tqps;
+ *max_rss_size = hdev->rss_size_max;
+}
+
+static void hclge_release_tqp(struct hclge_vport *vport)
+{
+ struct hnae3_knic_private_info *kinfo = &vport->nic.kinfo;
+ struct hclge_dev *hdev = vport->back;
+ int i;
+
+ for (i = 0; i < kinfo->num_tqps; i++) {
+ struct hclge_tqp *tqp =
+ container_of(kinfo->tqp[i], struct hclge_tqp, q);
+
+ tqp->q.handle = NULL;
+ tqp->q.tqp_index = 0;
+ tqp->alloced = false;
+ }
+
+ devm_kfree(&hdev->pdev->dev, kinfo->tqp);
+ kinfo->tqp = NULL;
+}
+
+static int hclge_set_channels(struct hnae3_handle *handle, u32 new_tqps_num)
+{
+ struct hclge_vport *vport = hclge_get_vport(handle);
+ struct hnae3_knic_private_info *kinfo = &vport->nic.kinfo;
+ struct hclge_dev *hdev = vport->back;
+ int cur_rss_size = kinfo->rss_size;
+ int cur_tqps = kinfo->num_tqps;
+ u16 tc_offset[HCLGE_MAX_TC_NUM];
+ u16 tc_valid[HCLGE_MAX_TC_NUM];
+ u16 tc_size[HCLGE_MAX_TC_NUM];
+ u16 roundup_size;
+ u32 *rss_indir;
+ int ret, i;
+
+ hclge_release_tqp(vport);
+
+ ret = hclge_knic_setup(vport, new_tqps_num);
+ if (ret) {
+ dev_err(&hdev->pdev->dev, "setup nic fail, ret =%d\n", ret);
+ return ret;
+ }
+
+ ret = hclge_map_tqp_to_vport(hdev, vport);
+ if (ret) {
+ dev_err(&hdev->pdev->dev, "map vport tqp fail, ret =%d\n", ret);
+ return ret;
+ }
+
+ ret = hclge_tm_schd_init(hdev);
+ if (ret) {
+ dev_err(&hdev->pdev->dev, "tm schd init fail, ret =%d\n", ret);
+ return ret;
+ }
+
+ roundup_size = roundup_pow_of_two(kinfo->rss_size);
+ roundup_size = ilog2(roundup_size);
+ /* Set the RSS TC mode according to the new RSS size */
+ for (i = 0; i < HCLGE_MAX_TC_NUM; i++) {
+ tc_valid[i] = 0;
+
+ if (!(hdev->hw_tc_map & BIT(i)))
+ continue;
+
+ tc_valid[i] = 1;
+ tc_size[i] = roundup_size;
+ tc_offset[i] = kinfo->rss_size * i;
+ }
+ ret = hclge_set_rss_tc_mode(hdev, tc_valid, tc_size, tc_offset);
+ if (ret)
+ return ret;
+
+ /* Reinitializes the rss indirect table according to the new RSS size */
+ rss_indir = kcalloc(HCLGE_RSS_IND_TBL_SIZE, sizeof(u32), GFP_KERNEL);
+ if (!rss_indir)
+ return -ENOMEM;
+
+ for (i = 0; i < HCLGE_RSS_IND_TBL_SIZE; i++)
+ rss_indir[i] = i % kinfo->rss_size;
+
+ ret = hclge_set_rss(handle, rss_indir, NULL, 0);
+ if (ret)
+ dev_err(&hdev->pdev->dev, "set rss indir table fail, ret=%d\n",
+ ret);
+
+ kfree(rss_indir);
+
+ if (!ret)
+ dev_info(&hdev->pdev->dev,
+ "Channels changed, rss_size from %d to %d, tqps from %d to %d",
+ cur_rss_size, kinfo->rss_size,
+ cur_tqps, kinfo->rss_size * kinfo->num_tc);
+
+ return ret;
+}
+
static const struct hnae3_ae_ops hclge_ops = {
.init_ae_dev = hclge_init_ae_dev,
.uninit_ae_dev = hclge_uninit_ae_dev,
@@ -5066,6 +5176,8 @@ static void hclge_get_channels(struct hnae3_handle *handle,
.set_vlan_filter = hclge_set_port_vlan_filter,
.set_vf_vlan_filter = hclge_set_vf_vlan_filter,
.reset_event = hclge_reset_event,
+ .get_tqps_and_rss_info = hclge_get_tqps_and_rss_info,
+ .set_channels = hclge_set_channels,
.get_channels = hclge_get_channels,
};
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 05/17] net: hns3: get rss_size_max from configuration but not hardcode
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
Add configuration for rss_size_max in hdev but not hardcode it.
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Mingguang Qu <qumingguang@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h | 2 ++
drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 6 +++++-
drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h | 1 +
3 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
index ce5ed88..1eb9ff0 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
@@ -399,6 +399,8 @@ struct hclge_pf_res_cmd {
#define HCLGE_CFG_MAC_ADDR_H_M GENMASK(15, 0)
#define HCLGE_CFG_DEFAULT_SPEED_S 16
#define HCLGE_CFG_DEFAULT_SPEED_M GENMASK(23, 16)
+#define HCLGE_CFG_RSS_SIZE_S 24
+#define HCLGE_CFG_RSS_SIZE_M GENMASK(31, 24)
struct hclge_cfg_param_cmd {
__le32 offset;
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index 7fab102..691f85e 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -982,6 +982,10 @@ static void hclge_parse_cfg(struct hclge_cfg *cfg, struct hclge_desc *desc)
cfg->default_speed = hnae_get_field(__le32_to_cpu(req->param[3]),
HCLGE_CFG_DEFAULT_SPEED_M,
HCLGE_CFG_DEFAULT_SPEED_S);
+ cfg->rss_size_max = hnae_get_field(__le32_to_cpu(req->param[3]),
+ HCLGE_CFG_RSS_SIZE_M,
+ HCLGE_CFG_RSS_SIZE_S);
+
for (i = 0; i < ETH_ALEN; i++)
cfg->mac_addr[i] = (mac_addr_tmp >> (8 * i)) & 0xff;
@@ -1059,7 +1063,7 @@ static int hclge_configure(struct hclge_dev *hdev)
hdev->num_vmdq_vport = cfg.vmdq_vport_num;
hdev->base_tqp_pid = 0;
- hdev->rss_size_max = 1;
+ hdev->rss_size_max = cfg.rss_size_max;
hdev->rx_buf_len = cfg.rx_buf_len;
ether_addr_copy(hdev->hw.mac.mac_addr, cfg.mac_addr);
hdev->hw.mac.media_type = cfg.media_type;
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h
index fb043b5..4858909 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h
@@ -220,6 +220,7 @@ struct hclge_cfg {
u8 tc_num;
u16 tqp_desc_num;
u16 rx_buf_len;
+ u16 rss_size_max;
u8 phy_addr;
u8 media_type;
u8 mac_addr[ETH_ALEN];
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 06/17] net: hns3: add a mask initialization for mac_vlan table
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
This patch sets vlan masked, in order to avoid the received
packets being filtered.
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Jian Shen <shenjian15@huawei.com>
---
.../net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h | 10 ++++++
.../ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 39 +++++++++++++++++++++-
2 files changed, 48 insertions(+), 1 deletion(-)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
index 1eb9ff0..10adf86 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
@@ -191,6 +191,7 @@ enum hclge_opcode_type {
HCLGE_OPC_MAC_VLAN_INSERT = 0x1003,
HCLGE_OPC_MAC_ETHTYPE_ADD = 0x1010,
HCLGE_OPC_MAC_ETHTYPE_REMOVE = 0x1011,
+ HCLGE_OPC_MAC_VLAN_MASK_SET = 0x1012,
/* Multicast linear table cmd */
HCLGE_OPC_MTA_MAC_MODE_CFG = 0x1020,
@@ -589,6 +590,15 @@ struct hclge_mac_vlan_tbl_entry_cmd {
u8 rsv2[6];
};
+#define HCLGE_VLAN_MASK_EN_B 0x0
+struct hclge_mac_vlan_mask_entry_cmd {
+ u8 rsv0[2];
+ u8 vlan_mask;
+ u8 rsv1;
+ u8 mac_mask[6];
+ u8 rsv2[14];
+};
+
#define HCLGE_CFG_MTA_MAC_SEL_S 0x0
#define HCLGE_CFG_MTA_MAC_SEL_M GENMASK(1, 0)
#define HCLGE_CFG_MTA_MAC_EN_B 0x7
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index 691f85e..a1d9398 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -2200,9 +2200,34 @@ static int hclge_get_autoneg(struct hnae3_handle *handle)
return hdev->hw.mac.autoneg;
}
+static int hclge_set_default_mac_vlan_mask(struct hclge_dev *hdev,
+ bool mask_vlan,
+ u8 *mac_mask)
+{
+ struct hclge_mac_vlan_mask_entry_cmd *req;
+ struct hclge_desc desc;
+ int status;
+
+ req = (struct hclge_mac_vlan_mask_entry_cmd *)desc.data;
+ hclge_cmd_setup_basic_desc(&desc, HCLGE_OPC_MAC_VLAN_MASK_SET, false);
+
+ hnae_set_bit(req->vlan_mask, HCLGE_VLAN_MASK_EN_B,
+ mask_vlan ? 1 : 0);
+ ether_addr_copy(req->mac_mask, mac_mask);
+
+ status = hclge_cmd_send(&hdev->hw, &desc, 1);
+ if (status)
+ dev_err(&hdev->pdev->dev,
+ "Config mac_vlan_mask failed for cmd_send, ret =%d\n",
+ status);
+
+ return status;
+}
+
static int hclge_mac_init(struct hclge_dev *hdev)
{
struct hclge_mac *mac = &hdev->hw.mac;
+ u8 mac_mask[ETH_ALEN] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
int ret;
ret = hclge_cfg_mac_speed_dup(hdev, hdev->hw.mac.speed, HCLGE_MAC_FULL);
@@ -2228,7 +2253,19 @@ static int hclge_mac_init(struct hclge_dev *hdev)
return ret;
}
- return hclge_cfg_func_mta_filter(hdev, 0, hdev->accept_mta_mc);
+ ret = hclge_cfg_func_mta_filter(hdev, 0, hdev->accept_mta_mc);
+ if (ret) {
+ dev_err(&hdev->pdev->dev,
+ "set mta filter mode fail ret=%d\n", ret);
+ return ret;
+ }
+
+ ret = hclge_set_default_mac_vlan_mask(hdev, true, mac_mask);
+ if (ret)
+ dev_err(&hdev->pdev->dev,
+ "set default mac_vlan_mask fail ret=%d\n", ret);
+
+ return ret;
}
static void hclge_mbx_task_schedule(struct hclge_dev *hdev)
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 07/17] net: hns3: add vlan offload config command
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
This patch adds vlan offload config commands, initializes
the rules of tx/rx vlan tag handle for hw.
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Jian Shen <shenjian15@huawei.com>
---
.../net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h | 45 ++++++
.../ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 158 ++++++++++++++++++++-
.../ethernet/hisilicon/hns3/hns3pf/hclge_main.h | 36 +++++
3 files changed, 233 insertions(+), 6 deletions(-)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
index 10adf86..f5baba21 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
@@ -180,6 +180,10 @@ enum hclge_opcode_type {
/* Promisuous mode command */
HCLGE_OPC_CFG_PROMISC_MODE = 0x0E01,
+ /* Vlan offload command */
+ HCLGE_OPC_VLAN_PORT_TX_CFG = 0x0F01,
+ HCLGE_OPC_VLAN_PORT_RX_CFG = 0x0F02,
+
/* Interrupts cmd */
HCLGE_OPC_ADD_RING_TO_VECTOR = 0x1503,
HCLGE_OPC_DEL_RING_TO_VECTOR = 0x1504,
@@ -670,6 +674,47 @@ struct hclge_vlan_filter_vf_cfg_cmd {
u8 vf_bitmap[16];
};
+#define HCLGE_ACCEPT_TAG_B 0
+#define HCLGE_ACCEPT_UNTAG_B 1
+#define HCLGE_PORT_INS_TAG1_EN_B 2
+#define HCLGE_PORT_INS_TAG2_EN_B 3
+#define HCLGE_CFG_NIC_ROCE_SEL_B 4
+struct hclge_vport_vtag_tx_cfg_cmd {
+ u8 vport_vlan_cfg;
+ u8 vf_offset;
+ u8 rsv1[2];
+ __le16 def_vlan_tag1;
+ __le16 def_vlan_tag2;
+ u8 vf_bitmap[8];
+ u8 rsv2[8];
+};
+
+#define HCLGE_REM_TAG1_EN_B 0
+#define HCLGE_REM_TAG2_EN_B 1
+#define HCLGE_SHOW_TAG1_EN_B 2
+#define HCLGE_SHOW_TAG2_EN_B 3
+struct hclge_vport_vtag_rx_cfg_cmd {
+ u8 vport_vlan_cfg;
+ u8 vf_offset;
+ u8 rsv1[6];
+ u8 vf_bitmap[8];
+ u8 rsv2[8];
+};
+
+struct hclge_tx_vlan_type_cfg_cmd {
+ __le16 ot_vlan_type;
+ __le16 in_vlan_type;
+ u8 rsv[20];
+};
+
+struct hclge_rx_vlan_type_cfg_cmd {
+ __le16 ot_fst_vlan_type;
+ __le16 ot_sec_vlan_type;
+ __le16 in_fst_vlan_type;
+ __le16 in_sec_vlan_type;
+ u8 rsv[16];
+};
+
struct hclge_cfg_com_tqp_queue_cmd {
__le16 tqp_id;
__le16 stream_id;
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index a1d9398..113b859 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -4380,23 +4380,169 @@ static int hclge_set_vf_vlan_filter(struct hnae3_handle *handle, int vfid,
return hclge_set_vf_vlan_common(hdev, vfid, false, vlan, qos, proto);
}
+static int hclge_set_vlan_tx_offload_cfg(struct hclge_vport *vport)
+{
+ struct hclge_tx_vtag_cfg *vcfg = &vport->txvlan_cfg;
+ struct hclge_vport_vtag_tx_cfg_cmd *req;
+ struct hclge_dev *hdev = vport->back;
+ struct hclge_desc desc;
+ int status;
+
+ hclge_cmd_setup_basic_desc(&desc, HCLGE_OPC_VLAN_PORT_TX_CFG, false);
+
+ req = (struct hclge_vport_vtag_tx_cfg_cmd *)desc.data;
+ req->def_vlan_tag1 = cpu_to_le16(vcfg->default_tag1);
+ req->def_vlan_tag2 = cpu_to_le16(vcfg->default_tag2);
+ hnae_set_bit(req->vport_vlan_cfg, HCLGE_ACCEPT_TAG_B,
+ vcfg->accept_tag ? 1 : 0);
+ hnae_set_bit(req->vport_vlan_cfg, HCLGE_ACCEPT_UNTAG_B,
+ vcfg->accept_untag ? 1 : 0);
+ hnae_set_bit(req->vport_vlan_cfg, HCLGE_PORT_INS_TAG1_EN_B,
+ vcfg->insert_tag1_en ? 1 : 0);
+ hnae_set_bit(req->vport_vlan_cfg, HCLGE_PORT_INS_TAG2_EN_B,
+ vcfg->insert_tag2_en ? 1 : 0);
+ hnae_set_bit(req->vport_vlan_cfg, HCLGE_CFG_NIC_ROCE_SEL_B, 0);
+
+ req->vf_offset = vport->vport_id / HCLGE_VF_NUM_PER_CMD;
+ req->vf_bitmap[req->vf_offset] =
+ 1 << (vport->vport_id % HCLGE_VF_NUM_PER_BYTE);
+
+ status = hclge_cmd_send(&hdev->hw, &desc, 1);
+ if (status)
+ dev_err(&hdev->pdev->dev,
+ "Send port txvlan cfg command fail, ret =%d\n",
+ status);
+
+ return status;
+}
+
+static int hclge_set_vlan_rx_offload_cfg(struct hclge_vport *vport)
+{
+ struct hclge_rx_vtag_cfg *vcfg = &vport->rxvlan_cfg;
+ struct hclge_vport_vtag_rx_cfg_cmd *req;
+ struct hclge_dev *hdev = vport->back;
+ struct hclge_desc desc;
+ int status;
+
+ hclge_cmd_setup_basic_desc(&desc, HCLGE_OPC_VLAN_PORT_RX_CFG, false);
+
+ req = (struct hclge_vport_vtag_rx_cfg_cmd *)desc.data;
+ hnae_set_bit(req->vport_vlan_cfg, HCLGE_REM_TAG1_EN_B,
+ vcfg->strip_tag1_en ? 1 : 0);
+ hnae_set_bit(req->vport_vlan_cfg, HCLGE_REM_TAG2_EN_B,
+ vcfg->strip_tag2_en ? 1 : 0);
+ hnae_set_bit(req->vport_vlan_cfg, HCLGE_SHOW_TAG1_EN_B,
+ vcfg->vlan1_vlan_prionly ? 1 : 0);
+ hnae_set_bit(req->vport_vlan_cfg, HCLGE_SHOW_TAG2_EN_B,
+ vcfg->vlan2_vlan_prionly ? 1 : 0);
+
+ req->vf_offset = vport->vport_id / HCLGE_VF_NUM_PER_CMD;
+ req->vf_bitmap[req->vf_offset] =
+ 1 << (vport->vport_id % HCLGE_VF_NUM_PER_BYTE);
+
+ status = hclge_cmd_send(&hdev->hw, &desc, 1);
+ if (status)
+ dev_err(&hdev->pdev->dev,
+ "Send port rxvlan cfg command fail, ret =%d\n",
+ status);
+
+ return status;
+}
+
+static int hclge_set_vlan_protocol_type(struct hclge_dev *hdev)
+{
+ struct hclge_rx_vlan_type_cfg_cmd *rx_req;
+ struct hclge_tx_vlan_type_cfg_cmd *tx_req;
+ struct hclge_desc desc;
+ int status;
+
+ hclge_cmd_setup_basic_desc(&desc, HCLGE_OPC_MAC_VLAN_TYPE_ID, false);
+ rx_req = (struct hclge_rx_vlan_type_cfg_cmd *)desc.data;
+ rx_req->ot_fst_vlan_type =
+ cpu_to_le16(hdev->vlan_type_cfg.rx_ot_fst_vlan_type);
+ rx_req->ot_sec_vlan_type =
+ cpu_to_le16(hdev->vlan_type_cfg.rx_ot_sec_vlan_type);
+ rx_req->in_fst_vlan_type =
+ cpu_to_le16(hdev->vlan_type_cfg.rx_in_fst_vlan_type);
+ rx_req->in_sec_vlan_type =
+ cpu_to_le16(hdev->vlan_type_cfg.rx_in_sec_vlan_type);
+
+ status = hclge_cmd_send(&hdev->hw, &desc, 1);
+ if (status) {
+ dev_err(&hdev->pdev->dev,
+ "Send rxvlan protocol type command fail, ret =%d\n",
+ status);
+ return status;
+ }
+
+ hclge_cmd_setup_basic_desc(&desc, HCLGE_OPC_MAC_VLAN_INSERT, false);
+
+ tx_req = (struct hclge_tx_vlan_type_cfg_cmd *)&desc.data;
+ tx_req->ot_vlan_type = cpu_to_le16(hdev->vlan_type_cfg.tx_ot_vlan_type);
+ tx_req->in_vlan_type = cpu_to_le16(hdev->vlan_type_cfg.tx_in_vlan_type);
+
+ status = hclge_cmd_send(&hdev->hw, &desc, 1);
+ if (status)
+ dev_err(&hdev->pdev->dev,
+ "Send txvlan protocol type command fail, ret =%d\n",
+ status);
+
+ return status;
+}
+
static int hclge_init_vlan_config(struct hclge_dev *hdev)
{
-#define HCLGE_VLAN_TYPE_VF_TABLE 0
-#define HCLGE_VLAN_TYPE_PORT_TABLE 1
+#define HCLGE_FILTER_TYPE_VF 0
+#define HCLGE_FILTER_TYPE_PORT 1
+#define HCLGE_DEF_VLAN_TYPE 0x8100
+
struct hnae3_handle *handle;
+ struct hclge_vport *vport;
int ret;
+ int i;
+
+ ret = hclge_set_vlan_filter_ctrl(hdev, HCLGE_FILTER_TYPE_VF, true);
+ if (ret)
+ return ret;
- ret = hclge_set_vlan_filter_ctrl(hdev, HCLGE_VLAN_TYPE_VF_TABLE,
- true);
+ ret = hclge_set_vlan_filter_ctrl(hdev, HCLGE_FILTER_TYPE_PORT, true);
if (ret)
return ret;
- ret = hclge_set_vlan_filter_ctrl(hdev, HCLGE_VLAN_TYPE_PORT_TABLE,
- true);
+ hdev->vlan_type_cfg.rx_in_fst_vlan_type = HCLGE_DEF_VLAN_TYPE;
+ hdev->vlan_type_cfg.rx_in_sec_vlan_type = HCLGE_DEF_VLAN_TYPE;
+ hdev->vlan_type_cfg.rx_ot_fst_vlan_type = HCLGE_DEF_VLAN_TYPE;
+ hdev->vlan_type_cfg.rx_ot_sec_vlan_type = HCLGE_DEF_VLAN_TYPE;
+ hdev->vlan_type_cfg.tx_ot_vlan_type = HCLGE_DEF_VLAN_TYPE;
+ hdev->vlan_type_cfg.tx_in_vlan_type = HCLGE_DEF_VLAN_TYPE;
+
+ ret = hclge_set_vlan_protocol_type(hdev);
if (ret)
return ret;
+ for (i = 0; i < hdev->num_alloc_vport; i++) {
+ vport = &hdev->vport[i];
+ vport->txvlan_cfg.accept_tag = true;
+ vport->txvlan_cfg.accept_untag = true;
+ vport->txvlan_cfg.insert_tag1_en = false;
+ vport->txvlan_cfg.insert_tag2_en = false;
+ vport->txvlan_cfg.default_tag1 = 0;
+ vport->txvlan_cfg.default_tag2 = 0;
+
+ ret = hclge_set_vlan_tx_offload_cfg(vport);
+ if (ret)
+ return ret;
+
+ vport->rxvlan_cfg.strip_tag1_en = false;
+ vport->rxvlan_cfg.strip_tag2_en = true;
+ vport->rxvlan_cfg.vlan1_vlan_prionly = false;
+ vport->rxvlan_cfg.vlan2_vlan_prionly = false;
+
+ ret = hclge_set_vlan_rx_offload_cfg(vport);
+ if (ret)
+ return ret;
+ }
+
handle = &hdev->vport[0].nic;
return hclge_set_port_vlan_filter(handle, htons(ETH_P_8021Q), 0, false);
}
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h
index 4858909..cda520c 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h
@@ -79,6 +79,10 @@
#define HCLGE_PHY_MDIX_STATUS_B (6)
#define HCLGE_PHY_SPEED_DUP_RESOLVE_B (11)
+/* Factor used to calculate offset and bitmap of VF num */
+#define HCLGE_VF_NUM_PER_CMD 64
+#define HCLGE_VF_NUM_PER_BYTE 8
+
/* Reset related Registers */
#define HCLGE_MISC_RESET_STS_REG 0x20700
#define HCLGE_GLOBAL_RESET_REG 0x20A00
@@ -424,6 +428,15 @@ struct hclge_hw_stats {
struct hclge_32_bit_stats all_32_bit_stats;
};
+struct hclge_vlan_type_cfg {
+ u16 rx_ot_fst_vlan_type;
+ u16 rx_ot_sec_vlan_type;
+ u16 rx_in_fst_vlan_type;
+ u16 rx_in_sec_vlan_type;
+ u16 tx_ot_vlan_type;
+ u16 tx_in_vlan_type;
+};
+
struct hclge_dev {
struct pci_dev *pdev;
struct hnae3_ae_dev *ae_dev;
@@ -510,6 +523,26 @@ struct hclge_dev {
enum hclge_mta_dmac_sel_type mta_mac_sel_type;
bool enable_mta; /* Mutilcast filter enable */
bool accept_mta_mc; /* Whether accept mta filter multicast */
+
+ struct hclge_vlan_type_cfg vlan_type_cfg;
+};
+
+/* VPort level vlan tag configuration for TX direction */
+struct hclge_tx_vtag_cfg {
+ bool accept_tag; /* Whether accept tagged packet from host */
+ bool accept_untag; /* Whether accept untagged packet from host */
+ bool insert_tag1_en; /* Whether insert inner vlan tag */
+ bool insert_tag2_en; /* Whether insert outer vlan tag */
+ u16 default_tag1; /* The default inner vlan tag to insert */
+ u16 default_tag2; /* The default outer vlan tag to insert */
+};
+
+/* VPort level vlan tag configuration for RX direction */
+struct hclge_rx_vtag_cfg {
+ bool strip_tag1_en; /* Whether strip inner vlan tag */
+ bool strip_tag2_en; /* Whether strip outer vlan tag */
+ bool vlan1_vlan_prionly;/* Inner VLAN Tag up to descriptor Enable */
+ bool vlan2_vlan_prionly;/* Outer VLAN Tag up to descriptor Enable */
};
struct hclge_vport {
@@ -524,6 +557,9 @@ struct hclge_vport {
u16 bw_limit; /* VSI BW Limit (0 = disabled) */
u8 dwrr;
+ struct hclge_tx_vtag_cfg txvlan_cfg;
+ struct hclge_rx_vtag_cfg rxvlan_cfg;
+
int vport_id;
struct hclge_dev *back; /* Back reference to associated dev */
struct hnae3_handle nic;
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 08/17] net: hns3: add ethtool related offload command
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
This patch adds offload command related to "ethtool -K".
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Jian Shen <shenjian15@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hnae3.h | 3 +++
drivers/net/ethernet/hisilicon/hns3/hns3_enet.c | 16 ++++++++++++++++
drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 13 +++++++++++++
3 files changed, 32 insertions(+)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hnae3.h b/drivers/net/ethernet/hisilicon/hns3/hnae3.h
index a5d3d22..a67d02a9 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hnae3.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hnae3.h
@@ -278,6 +278,8 @@ struct hnae3_ae_dev {
* Set vlan filter config of Ports
* set_vf_vlan_filter()
* Set vlan filter config of vf
+ * enable_hw_strip_rxvtag()
+ * Enable/disable hardware strip vlan tag of packets received
*/
struct hnae3_ae_ops {
int (*init_ae_dev)(struct hnae3_ae_dev *ae_dev);
@@ -384,6 +386,7 @@ struct hnae3_ae_ops {
u16 vlan_id, bool is_kill);
int (*set_vf_vlan_filter)(struct hnae3_handle *handle, int vfid,
u16 vlan, u8 qos, __be16 proto);
+ int (*enable_hw_strip_rxvtag)(struct hnae3_handle *handle, bool enable);
void (*reset_event)(struct hnae3_handle *handle,
enum hnae3_reset_type reset);
void (*get_channels)(struct hnae3_handle *handle,
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
index 1c93038..301b329 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
@@ -1032,6 +1032,9 @@ static int hns3_nic_set_features(struct net_device *netdev,
netdev_features_t features)
{
struct hns3_nic_priv *priv = netdev_priv(netdev);
+ struct hnae3_handle *h = priv->ae_handle;
+ netdev_features_t changed;
+ int ret;
if (features & (NETIF_F_TSO | NETIF_F_TSO6)) {
priv->ops.fill_desc = hns3_fill_desc_tso;
@@ -1041,6 +1044,17 @@ static int hns3_nic_set_features(struct net_device *netdev,
priv->ops.maybe_stop_tx = hns3_nic_maybe_stop_tx;
}
+ changed = netdev->features ^ features;
+ if (changed & NETIF_F_HW_VLAN_CTAG_RX) {
+ if (features & NETIF_F_HW_VLAN_CTAG_RX)
+ ret = h->ae_algo->ops->enable_hw_strip_rxvtag(h, true);
+ else
+ ret = h->ae_algo->ops->enable_hw_strip_rxvtag(h, false);
+
+ if (ret)
+ return ret;
+ }
+
netdev->features = features;
return 0;
}
@@ -1492,6 +1506,7 @@ static void hns3_set_default_feature(struct net_device *netdev)
netdev->features |= NETIF_F_IP_CSUM | NETIF_F_IPV6_CSUM |
NETIF_F_HW_VLAN_CTAG_FILTER |
+ NETIF_F_HW_VLAN_CTAG_TX | NETIF_F_HW_VLAN_CTAG_RX |
NETIF_F_RXCSUM | NETIF_F_SG | NETIF_F_GSO |
NETIF_F_GRO | NETIF_F_TSO | NETIF_F_TSO6 | NETIF_F_GSO_GRE |
NETIF_F_GSO_GRE_CSUM | NETIF_F_GSO_UDP_TUNNEL |
@@ -1506,6 +1521,7 @@ static void hns3_set_default_feature(struct net_device *netdev)
netdev->hw_features |= NETIF_F_IP_CSUM | NETIF_F_IPV6_CSUM |
NETIF_F_HW_VLAN_CTAG_FILTER |
+ NETIF_F_HW_VLAN_CTAG_TX | NETIF_F_HW_VLAN_CTAG_RX |
NETIF_F_RXCSUM | NETIF_F_SG | NETIF_F_GSO |
NETIF_F_GRO | NETIF_F_TSO | NETIF_F_TSO6 | NETIF_F_GSO_GRE |
NETIF_F_GSO_GRE_CSUM | NETIF_F_GSO_UDP_TUNNEL |
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index 113b859..d77a6de 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -4547,6 +4547,18 @@ static int hclge_init_vlan_config(struct hclge_dev *hdev)
return hclge_set_port_vlan_filter(handle, htons(ETH_P_8021Q), 0, false);
}
+static int hclge_en_hw_strip_rxvtag(struct hnae3_handle *handle, bool enable)
+{
+ struct hclge_vport *vport = hclge_get_vport(handle);
+
+ vport->rxvlan_cfg.strip_tag1_en = false;
+ vport->rxvlan_cfg.strip_tag2_en = enable;
+ vport->rxvlan_cfg.vlan1_vlan_prionly = false;
+ vport->rxvlan_cfg.vlan2_vlan_prionly = false;
+
+ return hclge_set_vlan_rx_offload_cfg(vport);
+}
+
static int hclge_set_mtu(struct hnae3_handle *handle, int new_mtu)
{
struct hclge_vport *vport = hclge_get_vport(handle);
@@ -5362,6 +5374,7 @@ static int hclge_set_channels(struct hnae3_handle *handle, u32 new_tqps_num)
.get_mdix_mode = hclge_get_mdix_mode,
.set_vlan_filter = hclge_set_port_vlan_filter,
.set_vf_vlan_filter = hclge_set_vf_vlan_filter,
+ .enable_hw_strip_rxvtag = hclge_en_hw_strip_rxvtag,
.reset_event = hclge_reset_event,
.get_tqps_and_rss_info = hclge_get_tqps_and_rss_info,
.set_channels = hclge_set_channels,
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 09/17] net: hns3: add handling vlan tag offload in bd
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
This patch deals with the vlan tag information between
sk_buff and rx/tx bd.
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Jian Shen <shenjian15@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hns3_enet.c | 83 +++++++++++++++++++++++--
1 file changed, 78 insertions(+), 5 deletions(-)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
index 301b329..320ae88 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
@@ -723,6 +723,58 @@ static void hns3_set_txbd_baseinfo(u16 *bdtp_fe_sc_vld_ra_ri, int frag_end)
hnae_set_field(*bdtp_fe_sc_vld_ra_ri, HNS3_TXD_SC_M, HNS3_TXD_SC_S, 0);
}
+static int hns3_fill_desc_vtags(struct sk_buff *skb,
+ struct hns3_enet_ring *tx_ring,
+ u32 *inner_vlan_flag,
+ u32 *out_vlan_flag,
+ u16 *inner_vtag,
+ u16 *out_vtag)
+{
+#define HNS3_TX_VLAN_PRIO_SHIFT 13
+
+ if (skb->protocol == htons(ETH_P_8021Q) &&
+ !(tx_ring->tqp->handle->kinfo.netdev->features &
+ NETIF_F_HW_VLAN_CTAG_TX)) {
+ /* When HW VLAN acceleration is turned off, and the stack
+ * sets the protocol to 802.1q, the driver just need to
+ * set the protocol to the encapsulated ethertype.
+ */
+ skb->protocol = vlan_get_protocol(skb);
+ return 0;
+ }
+
+ if (skb_vlan_tag_present(skb)) {
+ u16 vlan_tag;
+
+ vlan_tag = skb_vlan_tag_get(skb);
+ vlan_tag |= (skb->priority & 0x7) << HNS3_TX_VLAN_PRIO_SHIFT;
+
+ /* Based on hw strategy, use out_vtag in two layer tag case,
+ * and use inner_vtag in one tag case.
+ */
+ if (skb->protocol == htons(ETH_P_8021Q)) {
+ hnae_set_bit(*out_vlan_flag, HNS3_TXD_OVLAN_B, 1);
+ *out_vtag = vlan_tag;
+ } else {
+ hnae_set_bit(*inner_vlan_flag, HNS3_TXD_VLAN_B, 1);
+ *inner_vtag = vlan_tag;
+ }
+ } else if (skb->protocol == htons(ETH_P_8021Q)) {
+ struct vlan_ethhdr *vhdr;
+ int rc;
+
+ rc = skb_cow_head(skb, 0);
+ if (rc < 0)
+ return rc;
+ vhdr = (struct vlan_ethhdr *)skb->data;
+ vhdr->h_vlan_TCI |= cpu_to_be16((skb->priority & 0x7)
+ << HNS3_TX_VLAN_PRIO_SHIFT);
+ }
+
+ skb->protocol = vlan_get_protocol(skb);
+ return 0;
+}
+
static int hns3_fill_desc(struct hns3_enet_ring *ring, void *priv,
int size, dma_addr_t dma, int frag_end,
enum hns_desc_type type)
@@ -733,6 +785,8 @@ static int hns3_fill_desc(struct hns3_enet_ring *ring, void *priv,
u16 bdtp_fe_sc_vld_ra_ri = 0;
u32 type_cs_vlan_tso = 0;
struct sk_buff *skb;
+ u16 inner_vtag = 0;
+ u16 out_vtag = 0;
u32 paylen = 0;
u16 mss = 0;
__be16 protocol;
@@ -756,15 +810,16 @@ static int hns3_fill_desc(struct hns3_enet_ring *ring, void *priv,
skb = (struct sk_buff *)priv;
paylen = skb->len;
+ ret = hns3_fill_desc_vtags(skb, ring, &type_cs_vlan_tso,
+ &ol_type_vlan_len_msec,
+ &inner_vtag, &out_vtag);
+ if (unlikely(ret))
+ return ret;
+
if (skb->ip_summed == CHECKSUM_PARTIAL) {
skb_reset_mac_len(skb);
protocol = skb->protocol;
- /* vlan packet*/
- if (protocol == htons(ETH_P_8021Q)) {
- protocol = vlan_get_protocol(skb);
- skb->protocol = protocol;
- }
ret = hns3_get_l4_protocol(skb, &ol4_proto, &il4_proto);
if (ret)
return ret;
@@ -790,6 +845,8 @@ static int hns3_fill_desc(struct hns3_enet_ring *ring, void *priv,
cpu_to_le32(type_cs_vlan_tso);
desc->tx.paylen = cpu_to_le32(paylen);
desc->tx.mss = cpu_to_le16(mss);
+ desc->tx.vlan_tag = cpu_to_le16(inner_vtag);
+ desc->tx.outer_vlan_tag = cpu_to_le16(out_vtag);
}
/* move ring pointer to next.*/
@@ -2101,6 +2158,22 @@ static int hns3_handle_rx_bd(struct hns3_enet_ring *ring,
prefetchw(skb->data);
+ /* Based on hw strategy, the tag offloaded will be stored at
+ * ot_vlan_tag in two layer tag case, and stored at vlan_tag
+ * in one layer tag case.
+ */
+ if (netdev->features & NETIF_F_HW_VLAN_CTAG_RX) {
+ u16 vlan_tag;
+
+ vlan_tag = le16_to_cpu(desc->rx.ot_vlan_tag);
+ if (!(vlan_tag & VLAN_VID_MASK))
+ vlan_tag = le16_to_cpu(desc->rx.vlan_tag);
+ if (vlan_tag & VLAN_VID_MASK)
+ __vlan_hwaccel_put_tag(skb,
+ htons(ETH_P_8021Q),
+ vlan_tag);
+ }
+
bnum = 1;
if (length <= HNS3_RX_HEAD_SIZE) {
memcpy(__skb_put(skb, length), va, ALIGN(length, sizeof(long)));
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 10/17] net: hns3: cleanup mac auto-negotiation state query
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
From: Fuyun Liang <liangfuyun1@huawei.com>
When checking whether auto-negotiation is on, driver only needs to
check the value of mac.autoneg(SW) directly, and does not need to
query it from hardware. Because this value is always synchronized
with the auto-negotiation state of hardware.
This patch removes the mac auto-negotiation state query.
Signed-off-by: Fuyun Liang <liangfuyun1@huawei.com>
Signed-off-by: Peng Li <lipeng321@huawei.com>
---
.../ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 24 ----------------------
1 file changed, 24 deletions(-)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index d77a6de..046f4bb 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -2137,28 +2137,6 @@ static int hclge_query_mac_an_speed_dup(struct hclge_dev *hdev, int *speed,
return 0;
}
-static int hclge_query_autoneg_result(struct hclge_dev *hdev)
-{
- struct hclge_mac *mac = &hdev->hw.mac;
- struct hclge_query_an_speed_dup_cmd *req;
- struct hclge_desc desc;
- int ret;
-
- req = (struct hclge_query_an_speed_dup_cmd *)desc.data;
-
- hclge_cmd_setup_basic_desc(&desc, HCLGE_OPC_QUERY_AN_RESULT, true);
- ret = hclge_cmd_send(&hdev->hw, &desc, 1);
- if (ret) {
- dev_err(&hdev->pdev->dev,
- "autoneg result query cmd failed %d.\n", ret);
- return ret;
- }
-
- mac->autoneg = hnae_get_bit(req->an_syn_dup_speed, HCLGE_QUERY_AN_B);
-
- return 0;
-}
-
static int hclge_set_autoneg_en(struct hclge_dev *hdev, bool enable)
{
struct hclge_config_auto_neg_cmd *req;
@@ -2195,8 +2173,6 @@ static int hclge_get_autoneg(struct hnae3_handle *handle)
struct hclge_vport *vport = hclge_get_vport(handle);
struct hclge_dev *hdev = vport->back;
- hclge_query_autoneg_result(hdev);
-
return hdev->hw.mac.autoneg;
}
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 11/17] net: hns3: fix for getting auto-negotiation state in hclge_get_autoneg
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
From: Fuyun Liang <liangfuyun1@huawei.com>
When phy exists, we use the value of phydev.autoneg to represent the
auto-negotiation state of hardware. Otherwise, we use the value of
mac.autoneg to represent it.
This patch fixes for getting a error value of auto-negotiation state in
hclge_get_autoneg().
Fixes: 46a3df9f9718 ("net: hns3: Add HNS3 Acceleration Engine & Compatibility Layer Support")
Signed-off-by: Fuyun Liang <liangfuyun1@huawei.com>
Signed-off-by: Peng Li <lipeng321@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index 046f4bb..14e1054 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -2172,6 +2172,10 @@ static int hclge_get_autoneg(struct hnae3_handle *handle)
{
struct hclge_vport *vport = hclge_get_vport(handle);
struct hclge_dev *hdev = vport->back;
+ struct phy_device *phydev = hdev->hw.mac.phydev;
+
+ if (phydev)
+ return phydev->autoneg;
return hdev->hw.mac.autoneg;
}
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 15/17] net: hns3: add support for querying advertised pause frame by ethtool ethx
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
This patch adds support for querying advertised pause frame by using
ethtool command(ethtool ethx).
Fixes: 496d03e960ae ("net: hns3: Add Ethtool support to HNS3 driver")
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Fuyun Liang <liangfuyun1@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hnae3.h | 2 ++
drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c | 15 +++++++++++++++
drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 15 +++++++++++++++
3 files changed, 32 insertions(+)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hnae3.h b/drivers/net/ethernet/hisilicon/hns3/hnae3.h
index a67d02a9..82e9a80 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hnae3.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hnae3.h
@@ -394,6 +394,8 @@ struct hnae3_ae_ops {
void (*get_tqps_and_rss_info)(struct hnae3_handle *h,
u16 *free_tqps, u16 *max_rss_size);
int (*set_channels)(struct hnae3_handle *handle, u32 new_tqps_num);
+ void (*get_flowctrl_adv)(struct hnae3_handle *handle,
+ u32 *flowctrl_adv);
};
struct hnae3_dcb_ops {
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
index b829ec7..2ae4d39 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
@@ -575,6 +575,7 @@ static int hns3_get_link_ksettings(struct net_device *netdev,
struct ethtool_link_ksettings *cmd)
{
struct hnae3_handle *h = hns3_get_handle(netdev);
+ u32 flowctrl_adv = 0;
u32 supported_caps;
u32 advertised_caps;
u8 media_type = HNAE3_MEDIA_TYPE_UNKNOWN;
@@ -650,6 +651,8 @@ static int hns3_get_link_ksettings(struct net_device *netdev,
if (!cmd->base.autoneg)
advertised_caps &= ~HNS3_LM_AUTONEG_BIT;
+ advertised_caps &= ~HNS3_LM_PAUSE_BIT;
+
/* now, map driver link modes to ethtool link modes */
hns3_driv_to_eth_caps(supported_caps, cmd, false);
hns3_driv_to_eth_caps(advertised_caps, cmd, true);
@@ -662,6 +665,18 @@ static int hns3_get_link_ksettings(struct net_device *netdev,
/* 4.mdio_support */
cmd->base.mdio_support = ETH_MDIO_SUPPORTS_C22;
+ /* 5.get flow control setttings */
+ if (h->ae_algo->ops->get_flowctrl_adv)
+ h->ae_algo->ops->get_flowctrl_adv(h, &flowctrl_adv);
+
+ if (flowctrl_adv & ADVERTISED_Pause)
+ ethtool_link_ksettings_add_link_mode(cmd, advertising,
+ Pause);
+
+ if (flowctrl_adv & ADVERTISED_Asym_Pause)
+ ethtool_link_ksettings_add_link_mode(cmd, advertising,
+ Asym_Pause);
+
return 0;
}
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index bb31212..4d69688 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -4660,6 +4660,20 @@ static u32 hclge_get_fw_version(struct hnae3_handle *handle)
return hdev->fw_version;
}
+static void hclge_get_flowctrl_adv(struct hnae3_handle *handle,
+ u32 *flowctrl_adv)
+{
+ struct hclge_vport *vport = hclge_get_vport(handle);
+ struct hclge_dev *hdev = vport->back;
+ struct phy_device *phydev = hdev->hw.mac.phydev;
+
+ if (!phydev)
+ return;
+
+ *flowctrl_adv |= (phydev->advertising & ADVERTISED_Pause) |
+ (phydev->advertising & ADVERTISED_Asym_Pause);
+}
+
static void hclge_set_flowctrl_adv(struct hclge_dev *hdev, u32 rx_en, u32 tx_en)
{
struct phy_device *phydev = hdev->hw.mac.phydev;
@@ -5478,6 +5492,7 @@ static int hclge_set_channels(struct hnae3_handle *handle, u32 new_tqps_num)
.get_tqps_and_rss_info = hclge_get_tqps_and_rss_info,
.set_channels = hclge_set_channels,
.get_channels = hclge_get_channels,
+ .get_flowctrl_adv = hclge_get_flowctrl_adv,
};
static struct hnae3_ae_algo ae_algo = {
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 16/17] net: hns3: Increase the default depth of bucket for TM shaper
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
Burstiness of a flow is determined by the depth of a bucket, When the
upper rate of shaper is large, the current depth of a bucket is not
enough.
The default upper rate of shaper is 100G, so increase the depth of
a bucket according to UM.
Signed-off-by: Peng Li <lipeng321@huawei.com>
Signed-off-by: Yunsheng Lin <linyunsheng@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.c | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.c
index 7cfe1eb..ea9355d 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_tm.c
@@ -23,8 +23,8 @@ enum hclge_shaper_level {
HCLGE_SHAPER_LVL_PF = 1,
};
-#define HCLGE_SHAPER_BS_U_DEF 1
-#define HCLGE_SHAPER_BS_S_DEF 4
+#define HCLGE_SHAPER_BS_U_DEF 5
+#define HCLGE_SHAPER_BS_S_DEF 20
#define HCLGE_ETHER_MAX_RATE 100000
--
1.9.1
^ permalink raw reply related
* [PATCH V5 net-next 17/17] net: hns3: change TM sched mode to TC-based mode when SRIOV enabled
From: Peng Li @ 2017-12-22 4:21 UTC (permalink / raw)
To: davem; +Cc: netdev, linux-kernel, linuxarm, salil.mehta, lipeng321
In-Reply-To: <1513916516-104591-1-git-send-email-lipeng321@huawei.com>
TC-based sched mode supports SRIOV enabled and SRIOV disabled. This
patch change the TM sched mode to TC-based mode in initialization
process.
Fixes: cc9bb43ab394 ("net: hns3: Add tc-based TM support for sriov enabled port")
Signed-off-by: Peng Li <lipeng321@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 5 +----
1 file changed, 1 insertion(+), 4 deletions(-)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index 4d69688..0874acf 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -1100,10 +1100,7 @@ static int hclge_configure(struct hclge_dev *hdev)
for (i = 0; i < hdev->tm_info.num_tc; i++)
hnae_set_bit(hdev->hw_tc_map, i, 1);
- if (!hdev->num_vmdq_vport && !hdev->num_req_vfs)
- hdev->tx_sch_mode = HCLGE_FLAG_TC_BASE_SCH_MODE;
- else
- hdev->tx_sch_mode = HCLGE_FLAG_VNET_BASE_SCH_MODE;
+ hdev->tx_sch_mode = HCLGE_FLAG_TC_BASE_SCH_MODE;
return ret;
}
--
1.9.1
^ permalink raw reply related
* Re: [net] Revert "net: core: maybe return -EEXIST in __dev_alloc_name"
From: Michael Ellerman @ 2017-12-22 4:22 UTC (permalink / raw)
To: Rasmus Villemoes, Michael Ellerman
Cc: Jouni Malinen, netdev@vger.kernel.org, Johannes Berg,
linuxppc-dev@lists.ozlabs.org, Johannes Berg
In-Reply-To: <87efnpnf8b.fsf@rasmusvillemoes.dk>
Rasmus Villemoes <linux@rasmusvillemoes.dk> writes:
> On Tue, Dec 19 2017, Michael Ellerman <michael@concordia.ellerman.id.au> wrote:
>>> From: Johannes Berg <johannes.berg@intel.com>
>>>
>>> This reverts commit d6f295e9def0; some userspace (in the case
>>
>> This revert seems to have broken networking on one of my powerpc
>> machines, according to git bisect.
>>
>> The symptom is DHCP fails and I don't get a link, I didn't dig any
>> further than that. I can if it's helpful.
>>
>> I think the problem is that 87c320e51519 ("net: core: dev_get_valid_name
>> is now the same as dev_alloc_name_ns") only makes sense while
>> d6f295e9def0 remains in the tree.
>
> I'm sorry about all of this, I really didn't think there would be such
> consequences of changing an errno return. Indeed, d6f29 was preparation
> for unifying the two functions that do the exact same thing (and how we
> ever got into that situation is somewhat unclear), except for
> their behaviour in the case the requested name already exists. So one of
> the two interfaces had to change its return value, and as I wrote, I
> thought EEXIST was the saner choice when an explicit name (no %d) had
> been requested.
No worries.
>> ie. before the entire series, dev_get_valid_name() would return EEXIST,
>> and that was retained when 87c320e51519 was merged, but now that
>> d6f295e9def0 has been reverted dev_get_valid_name() is returning ENFILE.
>>
>> I can get the network up again if I also revert 87c320e51519 ("net:
>> core: dev_get_valid_name is now the same as dev_alloc_name_ns"), or with
>> the gross patch below.
>
> I don't think changing -ENFILE to -EEXIST would be right either, since
> dev_get_valid_name() used to be able to return both (-EEXIST in the case
> where there's no %d, -ENFILE in the case where we end up calling
> dev_alloc_name_ns()). If anything, we could do the check for the old
> -EEXIST condition first, and then call dev_alloc_name_ns(). But I'm also
> fine with reverting.
Yeah I think a revert would be best, given it's nearly rc5.
My userspace is not exotic AFAIK, just debian something, so presumably
this will affect other people too.
cheers
^ permalink raw reply
* Re: BUG: unable to handle kernel NULL pointer dereference in sctp_stream_free
From: Xin Long @ 2017-12-22 5:31 UTC (permalink / raw)
To: Marcelo Ricardo Leitner
Cc: syzbot, davem, LKML, linux-sctp, network dev, Neil Horman,
syzkaller-bugs, Vlad Yasevich
In-Reply-To: <20171221131333.GO6122@localhost.localdomain>
On Thu, Dec 21, 2017 at 9:13 PM, Marcelo Ricardo Leitner
<marcelo.leitner@gmail.com> wrote:
> On Wed, Dec 20, 2017 at 12:51:01PM -0800, syzbot wrote:
>
> from the log:
> [ 89.451366] FAULT_INJECTION: forcing a failure.^M
> [ 89.451366] name failslab, interval 1, probability 0, space 0,
> times 0^M
> [ 89.451374] CPU: 0 PID: 17287 Comm: syz-executor2 Not tainted
> +4.15.0-rc3-next-20171214+ #67^M
> [ 89.451377] Hardware name: Google Google Compute Engine/Google
> Compute Engine, BIOS
> +Google 01/01/2011^M
> [ 89.451380] Call Trace:^M
> [ 89.451395] dump_stack+0xe9/0x14b^M
> [ 89.451408] should_fail+0x1e5/0x220^M
> [ 89.451419] should_failslab+0x73/0x90^M
> [ 89.451428] __kmalloc+0x63/0x730^M
> [ 89.451439] ? rcu_read_lock_sched_held+0x74/0x80^M
> [ 89.451446] ? __kmalloc+0x4ac/0x730^M
> [ 89.451452] ? sctp_stream_alloc_in+0x2f/0x100^M
> [ 89.451464] sctp_stream_alloc_in+0x2f/0x100^M
> [ 89.451473] sctp_stream_init+0xfa/0x140^M
> [ 89.451485] sctp_process_init+0x676/0xc50^M
>
> this is what caused the panic later, because in the error path we free
> out but don't zero outcnt. This patch should fix it. Can you please
> try it? Thanks
>
> ----8<---
>
> diff --git a/net/sctp/stream.c b/net/sctp/stream.c
> index 06b644dd858c..50ab09029f00 100644
> --- a/net/sctp/stream.c
> +++ b/net/sctp/stream.c
> @@ -184,6 +184,7 @@ int sctp_stream_init(struct sctp_stream *stream, __u16 outcnt, __u16 incnt,
> sched->free(stream);
> kfree(stream->out);
> stream->out = NULL;
> + stream->outcnt = 0;
> out:
> return ret;
> }
In case it can't be verified due to no reproducer yet, I modified some
code in sctp_stream_init() to confirm Marcelo's deduction:
- i = sctp_stream_alloc_in(stream, incnt, gfp);
+ i = 1;
if (i) {
ret = -ENOMEM;
goto free;
And got the same call trace as the mail:
[ 301.488065] BUG: unable to handle kernel NULL pointer dereference
at 0000000000000008
[ 301.488618] IP: sctp_stream_free+0x2c/0x60 [sctp]
[ 301.488928] PGD 59a3b067 P4D 59a3b067 PUD 5994e067 PMD 0
[ 301.489372] Oops: 0000 [#1] SMP
[...]
[ 301.497647] Call Trace:
[ 301.497812] <IRQ>
[ 301.497955] sctp_association_free+0xb8/0x210 [sctp]
[ 301.498306] sctp_sf_do_5_1B_init+0x1c4/0x360 [sctp]
[ 301.498654] sctp_do_sm+0x9a/0x2d0 [sctp]
[ 301.498921] ? sctp_has_association+0x130/0x130 [sctp]
[ 301.499301] ? kernel_text_address+0xba/0xe0
[ 301.499615] ? check_usage_backwards+0x88/0x150
[ 301.499911] ? __lock_acquire+0x280/0x1080
[ 301.500200] ? sctp_endpoint_lookup_assoc+0x95/0x140 [sctp]
[ 301.500593] sctp_endpoint_bh_rcv+0x11e/0x220 [sctp]
[ 301.500923] sctp_rcv+0x9f5/0xbe0 [sctp]
And Marcelo's patch could fix it.
Since the "free:" part only works for if (i), maybe the patch can also do:
if (i) {
sched->free(stream);
kfree(stream->out);
stream->out = NULL;
stream->outcnt = 0;
ret = -ENOMEM;
goto out;
}
and remove the "free:" path.
^ permalink raw reply
* Re: [PATCH net] RDS: Check cmsg_len before dereferencing CMSG_DATA
From: santosh.shilimkar-QHcLZuEGTsvQT0dZR+AlfA @ 2017-12-22 6:58 UTC (permalink / raw)
To: Avinash Repaka, David S. Miller, netdev-u79uwXL29TY76Z2rM5mHXA,
linux-rdma-u79uwXL29TY76Z2rM5mHXA,
rds-devel-N0ozoZBvEnrZJqsBc5GL+g,
linux-kernel-u79uwXL29TY76Z2rM5mHXA
In-Reply-To: <1513916224-9445-1-git-send-email-avinash.repaka-QHcLZuEGTsvQT0dZR+AlfA@public.gmane.org>
On 12/21/17 8:17 PM, Avinash Repaka wrote:
> RDS currently doesn't check if the length of the control message is
> large enough to hold the required data, before dereferencing the control
> message data. This results in following crash:
>
> BUG: KASAN: stack-out-of-bounds in rds_rdma_bytes net/rds/send.c:1013
> [inline]
> BUG: KASAN: stack-out-of-bounds in rds_sendmsg+0x1f02/0x1f90
> net/rds/send.c:1066
> Read of size 8 at addr ffff8801c928fb70 by task syzkaller455006/3157
>
> CPU: 0 PID: 3157 Comm: syzkaller455006 Not tainted 4.15.0-rc3+ #161
> Hardware name: Google Google Compute Engine/Google Compute Engine, BIOS
> Google 01/01/2011
> Call Trace:
> __dump_stack lib/dump_stack.c:17 [inline]
> dump_stack+0x194/0x257 lib/dump_stack.c:53
> print_address_description+0x73/0x250 mm/kasan/report.c:252
> kasan_report_error mm/kasan/report.c:351 [inline]
> kasan_report+0x25b/0x340 mm/kasan/report.c:409
> __asan_report_load8_noabort+0x14/0x20 mm/kasan/report.c:430
> rds_rdma_bytes net/rds/send.c:1013 [inline]
> rds_sendmsg+0x1f02/0x1f90 net/rds/send.c:1066
> sock_sendmsg_nosec net/socket.c:628 [inline]
> sock_sendmsg+0xca/0x110 net/socket.c:638
> ___sys_sendmsg+0x320/0x8b0 net/socket.c:2018
> __sys_sendmmsg+0x1ee/0x620 net/socket.c:2108
> SYSC_sendmmsg net/socket.c:2139 [inline]
> SyS_sendmmsg+0x35/0x60 net/socket.c:2134
> entry_SYSCALL_64_fastpath+0x1f/0x96
> RIP: 0033:0x43fe49
> RSP: 002b:00007fffbe244ad8 EFLAGS: 00000217 ORIG_RAX: 0000000000000133
> RAX: ffffffffffffffda RBX: 00000000004002c8 RCX: 000000000043fe49
> RDX: 0000000000000001 RSI: 000000002020c000 RDI: 0000000000000003
> RBP: 00000000006ca018 R08: 0000000000000000 R09: 0000000000000000
> R10: 0000000000000000 R11: 0000000000000217 R12: 00000000004017b0
> R13: 0000000000401840 R14: 0000000000000000 R15: 0000000000000000
>
> To fix this, we verify that the cmsg_len is large enough to hold the
> data to be read, before proceeding further.
>
> Reported-by: syzbot <syzkaller-bugs-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org>
> Signed-off-by: Avinash Repaka <avinash.repaka-QHcLZuEGTsvQT0dZR+AlfA@public.gmane.org>
> ---
Thanks !!
Acked-by: Santosh Shilimkar <santosh.shilimkar-QHcLZuEGTsvQT0dZR+AlfA@public.gmane.org>
--
To unsubscribe from this list: send the line "unsubscribe linux-rdma" 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
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